Code Monkey home page Code Monkey logo

awslabs / amazon-kinesis-video-streams-webrtc-sdk-c Goto Github PK

View Code? Open in Web Editor NEW
994.0 52.0 297.0 625.02 MB

Amazon Kinesis Video Streams Webrtc SDK is for developers to install and customize realtime communication between devices and enable secure streaming of video, audio to Kinesis Video Streams.

Home Page: https://awslabs.github.io/amazon-kinesis-video-streams-webrtc-sdk-c/group__PublicMemberFunctions.html

License: Apache License 2.0

CMake 1.02% C 62.12% C++ 36.45% Shell 0.33% Python 0.07%
kinesis-video-streams webrtc-sdk webrtc

amazon-kinesis-video-streams-webrtc-sdk-c's Introduction

Amazon Kinesis Video Streams C WebRTC SDK

Pure C WebRTC Client for Amazon Kinesis Video Streams

Coverage Status

Key FeaturesBuildRunDocumentationSetup IoTUse Pre-generated CertificatesRelatedLicense

New feature announcements

Please refer to the release notes in Releases page

Key Features

  • Audio/Video Support
    • VP8
    • H264
    • Opus
    • G.711 PCM (A-law)
    • G.711 PCM (µ-law)
  • Developer Controlled Media Pipeline
  • DataChannels
  • NACKs
  • STUN/TURN Support
  • IPv4/IPv6
  • Signaling Client Included
    • KVS Provides STUN/TURN and Signaling Backend
    • Connect with Android/iOS/Web using pre-made samples
  • Storage for WebRTC [NEW]
    • Ingest media into a Kinesis Video Stream.
  • Portable
    • Tested on Linux/MacOS
    • Tested on x64, ARMv5
    • Build system designed for pleasant cross-compilation
  • Small Install Size
    • Sub 200k library size
    • OpenSSL, libsrtp, libjsmn, libusrsctp and libwebsockets dependencies.

Build

Download

To download run the following command:

git clone --recursive https://github.com/awslabs/amazon-kinesis-video-streams-webrtc-sdk-c.git

You will also need to install pkg-config and CMake and a build environment

Configuring on Ubuntu / Unix

Create a build directory in the newly checked out repository, and execute CMake from it.

mkdir -p amazon-kinesis-video-streams-webrtc-sdk-c/build; cd amazon-kinesis-video-streams-webrtc-sdk-c/build; cmake ..

We have provided an example of using GStreamer to capture/encode video, and then send via this library. This is only build if pkg-config finds GStreamer is installed on your system.

On Ubuntu and Raspberry Pi OS you can get the libraries by running

sudo apt-get install cmake m4 pkg-config libssl-dev libcurl4-openssl-dev liblog4cplus-dev libgstreamer1.0-dev libgstreamer-plugins-base1.0-dev gstreamer1.0-plugins-base-apps gstreamer1.0-plugins-bad gstreamer1.0-plugins-good gstreamer1.0-plugins-ugly gstreamer1.0-tools 

By default we download all the libraries from GitHub and build them locally, so should require nothing to be installed ahead of time. If you do wish to link to existing libraries you can use the following flags to customize your build.

Configuring on Windows

Install MS Visual Studio Community / Enterprise, Strawberry perl, and Chocolatey if not installed already

Get the libraries by running the following in powershell

choco install gstreamer
choco install gstreamer-devel
curl.exe -o C:\tools\pthreads-w32-2-9-1-release.zip ftp://sourceware.org/pub/pthreads-win32/pthreads-w32-2-9-1-release.zip
mkdir C:\tools\pthreads-w32-2-9-1-release\
Expand-Archive -Path C:\tools\pthreads-w32-2-9-1-release.zip -DestinationPath C:\tools\pthreads-w32-2-9-1-release

Modify the path to the downloaded and unzipped PThreads in cmake in build_windows_openssl.bat if needed / unzipped at a path other than the one mentioned above

cmake -G "NMake Makefiles" -DBUILD_TEST=TRUE -DEXT_PTHREAD_INCLUDE_DIR="C:/tools/pthreads-w32-2-9-1-release/Pre-built.2/include/" -DEXT_PTHREAD_LIBRARIES="C:/tools/pthreads-w32-2-9-1-release/Pre-built.2/lib/x64/libpthreadGC2.a" ..

Modify the path to MSVC as well in the build_windows_openssl.bat if needed / installed a different version / location

call "C:\Program Files\Microsoft Visual Studio\2022\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" x86_amd64

Allow long paths before we start the build

git config --system core.longpaths true

Note that if the paths are still too long (which can cause the build to fail unfortunately), we recommend renaming the folders to use shorter names and moving them to C:/

Build the SDK

.github\build_windows_openssl.bat

To run the sample application, make sure that you've exported the following paths and appended them to env:Path for powershell

$env:Path += ';C:\webrtc\open-source\bin;C:\tools\pthreads-w32-2-9-1-release\Pre-built.2\dll\x64;C:\webrtc\build'

Dependency requirements

These would be applicable if the SDK is being linked with system dependencies instead of building from source by the SDK. libmbedtls: >= 2.25.0 & < 3.x.x libopenssl: = 1.1.1x libsrtp2 : <= 2.5.0 libusrsctp : <= 0.9.5.0 libwebsockets : >= 4.2.0

Cross-Compilation

If you wish to cross-compile CC and CXX are respected when building the library and all its dependencies. You will also need to set BUILD_OPENSSL_PLATFORM, BUILD_LIBSRTP_HOST_PLATFORM and BUILD_LIBSRTP_DESTINATION_PLATFORM. See our codecov.io for an example of this. Every commit is cross compiled to ensure that it continues to work.

Static Builds

If -DBUILD_STATIC_LIBS=TRUE then all dependencies and KVS WebRTC libraries will be built as static libraries.

CMake Arguments

You can pass the following options to cmake ...

  • -DBUILD_STATIC_LIBS -- Build all KVS WebRTC and third-party libraries as static libraries.
  • -DADD_MUCLIBC -- Add -muclibc c flag
  • -DBUILD_DEPENDENCIES -- Whether or not to build depending libraries from source
  • -DBUILD_OPENSSL_PLATFORM -- If building OpenSSL what is the target platform
  • -DBUILD_LIBSRTP_HOST_PLATFORM -- If building LibSRTP what is the current platform
  • -DBUILD_LIBSRTP_DESTINATION_PLATFORM -- If building LibSRTP what is the destination platform
  • -DBUILD_TEST=TRUE -- Build unit/integration tests, may be useful for confirm support for your device. ./tst/webrtc_client_test
  • -DCODE_COVERAGE -- Enable coverage reporting
  • -DCOMPILER_WARNINGS -- Enable all compiler warnings
  • -DADDRESS_SANITIZER -- Build with AddressSanitizer
  • -DMEMORY_SANITIZER -- Build with MemorySanitizer
  • -DTHREAD_SANITIZER -- Build with ThreadSanitizer
  • -DUNDEFINED_BEHAVIOR_SANITIZER -- Build with UndefinedBehaviorSanitizer
  • -DCMAKE_BUILD_TYPE -- Build Release/Debug libraries. By default, the SDK generates Release build. The standard options are listed here
  • -DLINK_PROFILER -- Link with gperftools (available profiler options are listed here)
  • -DPKG_CONFIG_EXECUTABLE -- Set pkg config path. This might be required to find gstreamer's pkg config specifically on Windows.

To clean up the open-source and build folders from previous build, use cmake --build . --target clean from the build folder

For windows builds, you will have to include additional flags for libwebsockets CMake. Add the following flags to your cmake command, or edit the CMake file in ./CMake/Dependencies/libwebsockets-CMakeLists.txt with the following:

cmake .. -DLWS_HAVE_PTHREAD_H=1 -DLWS_EXT_PTHREAD_INCLUDE_DIR="C:\Program Files (x86)\pthreads\include" -DLWS_EXT_PTHREAD_LIBRARIES="C:\Program Files (x86)\pthreads\lib\x64\libpthreadGC2.a" -DLWS_WITH_MINIMAL_EXAMPLES=1

Be sure to edit the path to whatever pthread library you are using, and the proper path for your environment.

Build

To build the library and the provided samples run make in the build directory you executed CMake.

make

Building with dependencies off

In addition to the dependencies already installed, install the dependencies using the appropriate package manager.

On Ubuntu: sudo apt-get install libsrtp2-dev libusrsctp-dev libwebsockets-dev

On MacOS: brew install srtp libusrsctp libwebsockets

To use OpenSSL:

cmake .. -DBUILD_DEPENDENCIES=OFF -DUSE_OPENSSL=ON

To use MBedTLS:

cmake .. -DBUILD_DEPENDENCIES=OFF -DUSE_OPENSSL=OFF -DUSE_MBEDTLS=ON

Note: Please follow the dependency requirements to confirm the version requirements are satisfied to use the SDK with system installed dependencies. If the versions are not satisfied, this option would not work and enabling the SDK to build dependencies for you would be the best option to go ahead with.

Run

Setup your environment with your AWS account credentials and AWS region:

  • First set the appropriate environment variables so you can connect to KVS. If you want to use IoT certificate instead, check Setup IoT.
export AWS_ACCESS_KEY_ID=<AWS account access key>
export AWS_SECRET_ACCESS_KEY=<AWS account secret key>
  • Optionally, set AWS_SESSION_TOKEN if integrating with temporary token
export AWS_SESSION_TOKEN=<session token>
  • Region is optional, if not being set, then us-west-2 will be used as default region.
export AWS_DEFAULT_REGION=<AWS region>

Setup logging:

Set up the desired log level. The log levels and corresponding values currently available are:

  1. LOG_LEVEL_VERBOSE ---- 1
  2. LOG_LEVEL_DEBUG ---- 2
  3. LOG_LEVEL_INFO ---- 3
  4. LOG_LEVEL_WARN ---- 4
  5. LOG_LEVEL_ERROR ---- 5
  6. LOG_LEVEL_FATAL ---- 6
  7. LOG_LEVEL_SILENT ---- 7
  8. LOG_LEVEL_PROFILE ---- 8

To set a log level, run the following command:

export AWS_KVS_LOG_LEVEL=<LOG_LEVEL>

For example, the following command switches on DEBUG level logs while runnning the samples.

export AWS_KVS_LOG_LEVEL=2 

Note: The default log level is LOG_LEVEL_WARN.

Starting v1.8.0, by default, the SDK creates a log file that would have execution timing details of certain steps in connection establishment. It would be stored in the build directory as kvsFileLogFilter.x. In case you do not want to use defaults, you can modify certain parameters such as log file directory, log file size and file rotation index in the createFileLoggerWithLevelFiltering function in the samples. In addition to these logs, if you would like to have other level logs in a file as well, run:

export AWS_ENABLE_FILE_LOGGING=TRUE

The SDK also tracks entry and exit of functions which increases the verbosity of the logs. This will be useful when you want to track the transitions within the codebase. To do so, you need to set log level to LOG_LEVEL_VERBOSE and add the following to the CMakeLists.txt file: add_definitions(-DLOG_STREAMING) Note: This log level is extremely VERBOSE and could flood the files if using file based logging strategy.

Time-to-first-frame breakdown metrics

There is a flag in the sample application which (pSampleConfiguration->enableSendingMetricsToViewerViaDc) can be set to TRUE to send metrics from the master to the JS viewer. This helps get a detailed breakdown of time-to-first-frame and all the processes and API calls on master and the viewer both. This is intended to be used with the KVS WebRTC C SDK running as the master and the JS SDK as the viewer. The master sends peer, ice-agent, signaling and data-channel metrics to the viewer which are plotted ~ 20 seconds after the viewer is started. Since the timeline plot is intended to understand the time-to-first-frame, the sample web page needs to be refreshed and the master needs to be restarted if a new / updated plot is needed. While using the SDK in this mode, it is expected that all datachannel messages are JSON messages. This feature is only meant to be used for a single viewer at a time.

Set path to SSL CA certificate (Optional)

If you have a custom CA certificate path to set, you can set it using:

export AWS_KVS_CACERT_PATH=../certs/cert.pem

By defaut, the SSL CA certificate is set to ../certs/cert.pem which points to the file in this repository:

Running the Samples

After executing make you will have sample applications in your build/samples directory. From the build/ directory, run any of the sample applications by passing to it the name of your signaling channel. If a signaling channel does not exist with the name you provide, the application creates one.

Sample: kvsWebrtcClientMaster

This application sends sample H264/Opus frames (path: /samples/h264SampleFrames and /samples/opusSampleFrames) via WebRTC. It also accepts incoming audio, if enabled in the browser. When checked in the browser, it prints the metadata of the received audio packets in your terminal. To run:

./samples/kvsWebrtcClientMaster <channelName> <storage-option> <audio-codec> <video-codec>

To use the Storage for WebRTC feature, run the same command as above but with an additional command line arg to enable the feature.

./samples/kvsWebrtcClientMaster <channelName> 1 <audio-codec> <video-codec>

Allowed audio-codec: opus (default codec if nothing is specified) Allowed video-codec: h264 (default codec if nothing is specified), h265

Sample: kvsWebrtcClientMasterGstSample

This application can send media from a GStreamer pipeline using test H264/Opus frames, device autovideosrc and autoaudiosrc input, or a received RTSP stream. It also will playback incoming audio via an autoaudiosink. To run:

./samples/kvsWebrtcClientMasterGstSample <channelName> <mediaType> <sourceType>

Pass the desired media and source type when running the sample. The mediaType can be audio-video or video-only. To use the Storage For WebRTC feature, use audio-video-storage as the mediaType. The source type can be testsrc, devicesrc, or rtspsrc. Specify the RTSP URI if using rtspsrc:

./samples/kvsWebrtcClientMasterGstSample <channelName> <mediaType> rtspsrc rtsp://<rtspUri>

Using the testsrc with audio and video-codec

./samples/kvsWebrtcClientMasterGstSample <channelName> <mediaType> <sourceType> <audio-codec> <video-codec>

Example:

./samples/kvsWebrtcClientMasterGstSample <channelName> audio-video testsrc opus h264

Allowed audio-codec: opus (default codec if nothing is specified) Allowed video-codec: h264 (default codec if nothing is specified), h265

Sample: kvsWebrtcClientViewer

This application accepts sample H264/Opus frames by default. You can use other supported codecs by changing the value for videoTrack.codec and audioTrack.codec in Common.c. By default, this sample only logs the size of the audio and video buffer it receives. To write these frames to a file using GStreamer, use the kvsWebrtcClientViewerGstSample instead.

To run:

./samples/kvsWebrtcClientViewer <channelName> <audio-codec> <video-codec>

Allowed audio-codec: opus (default codec if nothing is specified) Allowed video-codec: h264 (default codec if nothing is specified), h265

Sample: kvsWebrtcClientViewerGstSample

This application is similar to the kvsWebrtcClientViewer. However, instead of just logging the media it receives, it generates a file using filesink. Make sure that your device has enough space to write the media to a file. You can also customize the receiving logic by modifying the functions in GstAudioVideoReceiver.c

To run:

./samples/kvsWebrtcClientViewerGstSample <channelName> <mediaType> <audio-codec> <video-codec>

Allowed audio-codec: opus (default codec if nothing is specified) Allowed video-codec: h264 (default codec if nothing is specified), h265

Known issues:

Our GStreamer samples leverage MatroskaMux to receive media from its peer and save it to a file. However, MatroskaMux is designed for scenarios where the media's format remains constant throughout streaming. When the media's format changes mid-streaming (referred to as "caps changes"), MatroskaMux encounters limitations, its behavior cannot be predicted and it may be unable to handle these changes, resulting in an error message like:

matroskamux matroska-mux.c:1134:gst_matroska_mux_video_pad_setcaps:<mux> error: Caps changes are not supported by Matroska

To address this issue, users need to adapt the pipeline to utilize components capable of managing dynamic changes in media formats. This might involve integrating different muxers or customizing the pipeline to handle caps changes effectively.

Sample: Generating sample frames

H264
gst-launch-1.0 videotestsrc pattern=ball num-buffers=1500 ! timeoverlay ! videoconvert ! video/x-raw,format=I420,width=1280,height=720,framerate=25/1 ! queue ! x264enc bframes=0 speed-preset=veryfast bitrate=512 byte-stream=TRUE tune=zerolatency ! video/x-h264,stream-format=byte-stream,alignment=au,profile=baseline ! multifilesink location="frame-%04d.h264" index=1
H265
gst-launch-1.0 videotestsrc pattern=ball num-buffers=1500 ! timeoverlay ! videoconvert ! video/x-raw,format=I420,width=1280,height=720,framerate=25/1 ! queue ! x265enc speed-preset=veryfast bitrate=512 tune=zerolatency ! video/x-h265,stream-format=byte-stream,alignment=au,profile=main ! multifilesink location="frame-%04d.h265" index=1

Viewing Master Samples

After running one of the master samples, when the command line application prints "Signaling client connection to socket established", indicating that your signaling channel is created and the connected master is streaming media to it, you can view the stream. To do so, check the media playback viewer on the KVS Signaling Channels console or open the WebRTC SDK Test Page.

If using the WebRTC SDK Test Page, set the following values using the same AWS credentials and the same signaling channel that you specified for the master above:

  • Access key ID
  • Secret access key
  • Signaling channel name
  • Client ID (optional)

Then choose Start Viewer to start live video streaming of the sample H264/Opus frames.

Setup IoT

{
   "Version":"2012-10-17",
   "Statement":[
      {
          "Effect":"Allow",
          "Action":[
            "kinesisvideo:DescribeSignalingChannel",
            "kinesisvideo:CreateSignalingChannel",
            "kinesisvideo:GetSignalingChannelEndpoint",
            "kinesisvideo:GetIceServerConfig",
            "kinesisvideo:ConnectAsMaster"
          ],
          "Resource":"arn:aws:kinesisvideo:*:*:channel/${credentials-iot:ThingName}/*"
      }
   ]
}

We recommend following best practices while setting up the IAM policy and not allow access to all channels in the account, but allow access to only the REQUIRED channel names if the use case demands it. KVS recommendation is to use iot thing name as channel name as per public docs. https://docs.aws.amazon.com/kinesisvideostreams/latest/dg/how-iot.html

Note: "kinesisvideo:CreateSignalingChannel" can be removed if you are running with existing KVS signaling channels. Viewer sample requires "kinesisvideo:ConnectAsViewer" permission. Integration test requires both "kinesisvideo:ConnectAsViewer" and "kinesisvideo:DeleteSignalingChannel" permission.

  • With the IoT certificate, IoT credentials provider endpoint (Note: it is not the endpoint on IoT AWS Console!), public key and private key ready, you can replace the static credentials provider createStaticCredentialProvider() and freeStaticCredentialProvider() with IoT credentials provider like below, the credentials provider for samples is in createSampleConfiguration():
createLwsIotCredentialProvider(
            "coxxxxxxxx168.credentials.iot.us-west-2.amazonaws.com",  // IoT credentials endpoint
            "/Users/username/Downloads/iot-signaling/certificate.pem",  // path to iot certificate
            "/Users/username/Downloads/iot-signaling/private.pem.key", // path to iot private key
            "/Users/username/Downloads/iot-signaling/cacert.pem", // path to CA cert
            "KinesisVideoSignalingCameraIoTRoleAlias", // IoT role alias
            "IoTThingName", // iot thing name, recommended to be same as your channel name
            &pSampleConfiguration->pCredentialProvider));

freeIotCredentialProvider(&pSampleConfiguration->pCredentialProvider);

TWCC support

Transport Wide Congestion Control (TWCC) is a mechanism in WebRTC designed to enhance the performance and reliability of real-time communication over the internet. TWCC addresses the challenges of network congestion by providing detailed feedback on the transport of packets across the network, enabling adaptive bitrate control and optimization of media streams in real-time. This feedback mechanism is crucial for maintaining high-quality audio and video communication, as it allows senders to adjust their transmission strategies based on comprehensive information about packet losses, delays, and jitter experienced across the entire transport path.

The importance of TWCC in WebRTC lies in its ability to ensure efficient use of available network bandwidth while minimizing the negative impacts of network congestion. By monitoring the delivery of packets across the network, TWCC helps identify bottlenecks and adjust the media transmission rates accordingly. This dynamic approach to congestion control is essential for preventing degradation in call quality, such as pixelation, stuttering, or drops in audio and video streams, especially in environments with fluctuating network conditions.

To learn more about TWCC, check TWCC spec

Enabling TWCC support

TWCC is enabled by default in the SDK samples (via pSampleConfiguration->enableTwcc) flag. In order to disable it, set this flag to FALSE.

pSampleConfiguration->enableTwcc = FALSE;

If not using the samples directly, 2 things need to be done to set up Twcc:

  1. Set the disableSenderSideBandwidthEstimation to FALSE:
configuration.kvsRtcConfiguration.disableSenderSideBandwidthEstimation = FALSE;
  1. Set the callback that will have the business logic to modify the bitrate based on packet loss information. The callback can be set using peerConnectionOnSenderBandwidthEstimation():
CHK_STATUS(peerConnectionOnSenderBandwidthEstimation(pSampleStreamingSession->pPeerConnection, (UINT64) pSampleStreamingSession,
                                                     sampleSenderBandwidthEstimationHandler));

Use Pre-generated Certificates

The certificate generating function (createCertificateAndKey) in createDtlsSession() can take between 5 - 15 seconds in low performance embedded devices, it is called for every peer connection creation when KVS WebRTC receives an offer. To avoid this extra start-up latency, certificate can be pre-generated and passed in when offer comes.

Important Note: It is recommended to rotate the certificates often - preferably for every peer connection to avoid a compromised client weakening the security of the new connections.

Take kvsWebRTCClientMaster as sample, add RtcCertificate certificates[CERT_COUNT]; to SampleConfiguration in Samples.h. Then pass in the pre-generated certificate in initializePeerConnection() in Common.c.

configuration.certificates[0].pCertificate = pSampleConfiguration->certificates[0].pCertificate;
configuration.certificates[0].pPrivateKey = pSampleConfiguration->certificates[0].pPrivateKey;

where, configuration is of type RtcConfiguration in the function that calls initializePeerConnection().

Doing this will make sure that createCertificateAndKey() would not execute since a certificate is already available.

Provide Hardware Entropy Source

In the mbedTLS version, the SDK uses /dev/urandom on Unix and CryptGenRandom API on Windows to get a strong entropy source. On some systems, these APIs might not be available. So, it's strongly suggested that you bring your own hardware entropy source. To do this, you need to follow these steps:

  1. Uncomment MBEDTLS_ENTROPY_HARDWARE_ALT in configs/config_mbedtls.h
  2. Write your own entropy source implementation by following this function signature: https://github.com/ARMmbed/mbedtls/blob/v2.25.0/include/mbedtls/entropy_poll.h#L81-L92
  3. Include your implementation source code in the linking process

DEBUG

Getting the SDPs

If you would like to print out the SDPs, run this command: export DEBUG_LOG_SDP=TRUE

Adjust MTU

If ICE connection can be established successfully but media can not be transferred, make sure the actual MTU is higher than the MTU setting here: https://github.com/awslabs/amazon-kinesis-video-streams-webrtc-sdk-c/blob/master/src/source/PeerConnection/Rtp.h#L12.

You can also change settings such as buffer size, number of log files for rotation and log file path in the samples

Clang Checks

This SDK has clang format checks enforced in builds. In order to avoid re-iterating and make sure your code complies, use the scripts/check-clang.sh to check for compliance and scripts/clang-format.sh to ensure compliance.

Tracing high memory and/or cpu usage

If you would like to specifically find the code path that causes high memory and/or cpu usage, you need to recompile the SDK with this command: cmake .. -DLINK_PROFILER=ON

The flag will link the SDK with gperftools profiler.

Heap Profile

You can run your program as you normally would. You only need to specify the following environment variable to get the heap profile:

HEAPPROFILE=/tmp/heap.prof /path/to/your/binary

More information about what environment variables you can configure can be found here

CPU Profile

Similar to the heap profile, you only need to specify the following environment variable to get the CPU profile:

CPUPROFILE=/tmp/cpu.prof /path/to/your/binary

More information about what environment variables you can configure can be found here

Filtering network interfaces

This is useful to reduce candidate gathering time when it is known for certain network interfaces to not work well. A sample callback is available in Common.c. The iceSetInterfaceFilterFunc in KvsRtcConfiguration must be set to the required callback. In the sample, it can be done this way in initializePeerConnection(): configuration.kvsRtcConfiguration.iceSetInterfaceFilterFunc = sampleFilterNetworkInterfaces

Building on MacOS M1

When building on MacOS M1, if the build fails while trying to build OpenSSL or Websockets, run the following command: cmake .. -DBUILD_OPENSSL_PLATFORM=darwin64-arm64-cc

Building on 32 bit Raspbian GNU/Linux 11

To build on a 32-bit Raspbian GNU/Linux 11 on 64-bit hardware, the OpenSSL library must be manually configured. This is due to the OpenSSL autoconfiguration script detecting 64-bit hardware and emitting 64-bit ARM assembly instructions which are not allowed in 32-bit executables. A 32-bit ARM version of OpenSSL can be configured by setting 32-bit ARM platform: cmake .. -DBUILD_OPENSSL_PLATFORM=linux-armv4

Threadpool for the SDK

The threadpool is enabled by default, and starts with 3 threads that it can increase up to 10 if all are actively in use. To change these values to better match the resources of your use case you can set the environment variables to do so:

  1. export AWS_KVS_WEBRTC_THREADPOOL_MIN_THREADS=<value>
  2. export AWS_KVS_WEBRTC_THREADPOOL_MAX_THREADS=<value>

To disable threadpool, run cmake .. -DENABLE_KVS_THREADPOOL=OFF

Starting version 1.10.0, threadpool usage provides latency improvements in connection establishment. Note, that increasing the number of minimum threads can increase stack memory usage. So, ensure to increase with caution.

Set up TWCC

TWCC is a mechanism in WebRTC designed to enhance the performance and reliability of real-time communication over the Internet. TWCC addresses the challenges of network congestion by providing detailed feedback on the transport of packets across the network, enabling adaptive bitrate control and optimization of media streams in real-time. This feedback mechanism is crucial for maintaining high-quality audio and video communication, as it allows senders to adjust their transmission strategies based on comprehensive information about packet losses, delays, and jitter experienced across the entire transport path. The importance of TWCC in WebRTC lies in its ability to ensure efficient use of available network bandwidth while minimizing the negative impacts of network congestion. By monitoring the delivery of packets across the network, TWCC helps identify bottlenecks and adjust the media transmission rates accordingly. This dynamic approach to congestion control is essential for preventing degradation in call quality, such as pixelation, stuttering, or drops in audio and video streams, especially in environments with fluctuating network conditions. To learn more about TWCC, you can refer to the RFC draft

In order to enable TWCC usage in the SDK, 2 things need to be set up:

  1. Set the disableSenderSideBandwidthEstimation to FALSE. In our samples, the value is set using enableTwcc flag in pSampleConfiguration
pSampleConfiguration->enableTwcc = TRUE; // to enable TWCC
pSampleConfiguration->enableTwcc = FALSE; // to disable TWCC
configuration.kvsRtcConfiguration.disableSenderSideBandwidthEstimation = !pSampleConfiguration->enableTwcc;
  1. Set the callback that will have the business logic to modify the bitrate based on packet loss information. The callback can be set using peerConnectionOnSenderBandwidthEstimation().
CHK_STATUS(peerConnectionOnSenderBandwidthEstimation(pSampleStreamingSession->pPeerConnection, (UINT64) pSampleStreamingSession,
                                                     sampleSenderBandwidthEstimationHandler));

By default, our SDK enables TWCC listener. The SDK has a sample implementation to integrate TWCC into the Gstreamer pipeline via the sampleSenderBandwidthEstimationHandler callback. To get more details, look for this specific callback.

Setting ICE related timeouts

There are some default timeout values set for different steps in ICE in the KvsRtcConfiguration. These are configurable in the application. While the defaults are generous, there could be applications that might need more flexibility to improve chances of connection establishment because of poor network.

You can find the default setting in the logs:

2024-01-08 19:43:44.433 INFO    iceAgentValidateKvsRtcConfig():
	iceLocalCandidateGatheringTimeout: 10000 ms
	iceConnectionCheckTimeout: 12000 ms
	iceCandidateNominationTimeout: 12000 ms
	iceConnectionCheckPollingInterval: 50 ms

Let us look into when each of these could be changed:

  1. iceCandidateNominationTimeout: Say the connection with host/srflx could not be established and TURN seems to be the only resort. Let us assume it takes about 15 seconds to gather the first local relay candidate, the application could set the timeout to a value more than 15 seconds to ensure candidate pairs with the local relay candidate are tried for success. If the value is set to less than 15 seconds in this case, the SDK would lose out on trying a potential candidate pair leading to connection establishment failure
  2. iceLocalCandidateGatheringTimeout: Say the host candidates would not work and srflx/relay candidates need to be tried. Due to poor network, it is anticipated the candidates are gathered slowly and the application does not want to spend more than 20 seconds on this step. The goal is to try all possible candidate pairs. Increasing the timeout helps in giving some more time to gather more potential candidates to try for connection. Also note, this parameter increase would not make a difference in the situation unless iceCandidateNominationTimeout > iceLocalCandidateGatheringTimeout since nomination step should also be given time to work with the new candidates
  3. iceConnectionCheckTimeout: It is useful to increase this timeout in unstable/slow network where the packet exchange takes time and hence the binding request/response. Essentially, increasing it will allow atleast one candidate pair to be tried for nomination by the other peer.
  4. iceConnectionCheckPollingInterval: This value is set to a default of 50 ms per spec. Changing this would change the frequency of connectivity checks and essentially, the ICE state machine transitions. Decreasing the value could help in faster connection establishment in a reliable high performant network setting with good system resources. Increasing the value could help in reducing the network load, however, the connection establishment could slow down. Unless there is a strong reasoning, it is NOT recommended to deviate from spec/default.

Documentation

All Public APIs are documented in our Include.h, we also generate a Doxygen each commit for easier navigation.

Refer to related for more about WebRTC and KVS.

Development

If you would like to contribute to the development of this project, please base your pull requests off of the origin/develop branch, and to the origin/develop branch. Commits from develop will be merged into master periodically as a part of each release cycle.

Outbound hostname and port requirements

  • KVS endpoint : TCP 443 (ex: kinesisvideo.us-west-2.amazonaws.com)
  • HTTPS channel endpoint : TCP 443 (ex: r-2c136a55.kinesisvideo.us-west-2.amazonaws.com)
  • WSS channel endpoint : TCP 443 (ex: m-26d02974.kinesisvideo.us-west-2.amazonaws.com)
  • STUN endpoint : UDP 443 (ex: stun.kinesisvideo.us-west-2.amazonaws.com)
  • TURN endpoint : UDP/TCP 443 (ex: 34-219-91-62.t-1cd92f6b.kinesisvideo.us-west-2.amazonaws.com:443)

The least common denominator for hostname is *.kinesisvideo.<region>.amazonaws.com and port is 443.

Related

License

This library is licensed under the Apache 2.0 License.

amazon-kinesis-video-streams-webrtc-sdk-c's People

Contributors

andyhoffy avatar bkneff avatar chehefen avatar codingspirit avatar disa6302 avatar ek9852 avatar ela34 avatar enobufs avatar fernandoc1 avatar grahn avatar hassanctech avatar jamesiri avatar jdelapla avatar kev-the-dev avatar lherman-cs avatar mateuszboryn avatar mushmal avatar nicholas-stpierre-simplisafe avatar niyatim23 avatar nomidia avatar northteam avatar sean-der avatar suggestedfixes avatar timgates42 avatar unicornss avatar ycyang1229 avatar yuma-m avatar zhiyua-git avatar zhuker avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

amazon-kinesis-video-streams-webrtc-sdk-c's Issues

IPv6 Support

We need IPv6 support, we should allow the user to opt in/out. In some cases you have IPv6, but all packets are discarded so just causes spam in the logs.

Make ICE timing configurable

Users may have unique requirements in certain networks, we should make the following configurable per PeerConnection

  • ICE timeout intervals (may prefer to fail fast)
  • Polling Intervals (May have a very lossy network, or working in a network constrained env)
  • Custom configuration for nomination (how soon till we nominate, if we use TURN and don't even attempt host/reflexive candidates)

Do it fall back to use turn server automatically ?

We notice that STATUS createSampleConfiguration(PCHAR channelName, SIGNALING_CHANNEL_ROLE_TYPE roleType, BOOL trickleIce, BOOL useTurn, PSampleConfiguration* ppSampleConfiguration)
It needs to specify useTURN or not.

Doesn't the sdk SHOULD fall back to use TURN server automatically when p2p between device cannot be reached ? If so, why there is a setting or that .

Unable to use WebRTC SDK Test Page for testing

Hi @Sean-Der

Follow the file README.md

`When the command line application prints Connection established, you can proceed to the next step.

Now that your signaling channel is created and the connected master is streaming media to it, you can view this stream. To do so, open the WebRTC SDK Test Page using the steps in Using the Kinesis Video Streams with WebRTC Test Page and set the following values using the same AWS credentials and the same signaling channel that you specified for the master above:

  • Access key ID
  • Secret access key
  • Signaling channel name
  • Client ID (optional)

Choose Start viewer to start live video streaming of the sample H264/Opus frames`

Ubuntu-16.04 log

Ubuntu_Unable-to-use-WebRTC_SDK_Test_Page-for-testing_20200109.txt

[WebRTC SDK Test Page] log

[2020-01-09T06:37:03.997Z] [INFO] Page loaded [2020-01-09T06:38:05.914Z] [INFO] [VIEWER] Channel ARN: arn:aws:kinesisvideo:us-west-2:380632319579:channel/ScaryTestChannel/1577439476380

This situation only appeared in the updated version on January 8, 2020, which did not exist before.
The original SDK version was updated on December 27, 2019

I think I need your help. Thank you.

Don't use PiC functions in samples

We don't want to push users to write code a certain way when using our samples, we should rewrite to look like idiomatic C.

We can keep the same patterns of CleanUp: but CHK_STATUS and other things like that should be avoided.

sendto: "No route to host" in iceUtilsSendStunPacket, getInt16 on macos

Hi! I'm tying to use aws webrtc with my own signal channel via mqtt
I get an infinite loop with error "sendto: No route to host" when i set remote offer to local peerclient

configuration.iceServers[0].urls: stun:stun.l.google.com:19302
2020-01-09 21:52:14 DEBUG   iceAgentValidateKvsRtcConfig(): 
	iceLocalCandidateGatheringTimeout: 10000 ms
	iceConnectionCheckTimeout: 10000 ms
	iceCandidateNominationTimeout: 10000 ms
	iceConnectionCheckPollingInterval: 50 ms
2020-01-09 21:52:14 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_NONE to ICE_AGENT_STATE_NEW.
2020-01-09 21:52:14 DEBUG   stepStateMachine(): State Machine - Current state: 0x0000000000000001, Next state: 0x0000000000000002
2020-01-09 21:52:14 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_NEW to ICE_AGENT_STATE_GATHERING.
2020-01-09 21:52:14 DEBUG   onConnectionStateChange(): New connection state 1
2020-01-09 21:52:14 DEBUG   socketConnectionSendData(): sendto data failed with errno No route to host
2020-01-09 21:52:14 DEBUG   iceUtilsSendStunPacket(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   iceAgentStateGatheringTimerCallback(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   timerQueueExecutor(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   updateCandidateAddress(): New server reflexive candidate found
2020-01-09 21:52:14 DEBUG   socketConnectionSendData(): sendto data failed with errno No route to host
2020-01-09 21:52:14 DEBUG   iceUtilsSendStunPacket(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   iceAgentStateGatheringTimerCallback(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   timerQueueExecutor(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   socketConnectionSendData(): sendto data failed with errno No route to host
2020-01-09 21:52:14 DEBUG   iceUtilsSendStunPacket(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   iceAgentStateGatheringTimerCallback(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   timerQueueExecutor(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   socketConnectionSendData(): sendto data failed with errno No route to host
2020-01-09 21:52:14 DEBUG   iceUtilsSendStunPacket(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   iceAgentStateGatheringTimerCallback(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   timerQueueExecutor(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   socketConnectionSendData(): sendto data failed with errno No route to host
2020-01-09 21:52:14 DEBUG   iceUtilsSendStunPacket(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   iceAgentStateGatheringTimerCallback(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   timerQueueExecutor(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   socketConnectionSendData(): sendto data failed with errno No route to host
2020-01-09 21:52:14 DEBUG   iceUtilsSendStunPacket(): operation returned status code: 0x5800001a
2020-01-09 21:52:14 DEBUG   iceAgentStateGatheringTimerCallback(): operation returned status code: 0x5800001a

i found this line

pIceServer->ipAddress.port = (UINT16) getInt16((INT16) port);

and run simple check:

    printf("port %d\n", port);
    pIceServer->ipAddress.port = (UINT16) getInt16((INT16) port);
    printf("pIceServer->ipAddress.port %d\n", pIceServer->ipAddress.port);

output:

port 19302
pIceServer->ipAddress.port 26187

Is it correct value? My platform is macos core i7 intel 64bit
when i removed getInt16 call i still getting the same infinite loop..

Do you have any plans to create minimal samples without signal library?
for example peer 2 peer datachannel like in pion library with simple copy/paste offers in console or maby only one sender in C and js on jsfiddle as client with copy/paste as signal channel?
I will trying to build something like that

Enable EOR for SCTP

Currently we don't support EOR, you can read it about it here

Until we do our message size is capped at a single SCTP CHUNK.

Sdk crashes when new PeerConnection establishes new connection

Steps to reproduce:

  • start kvsWebrtcClientMasterSample with any channel name.
  • start js viewer in any connection mode. Ensure data channel is enabled. Connection should be established successfully and starts streaming.
  • stop the js viewer.
  • wait until connectionStateChange callback is called and trigger peerConnection teardown, the following log should be seen
2019-12-07 01:53:57 DEBUG   main(): Completed freeing peerConnection and Reinitializing peerConnection
2019-12-07 01:53:57 VERBOSE signalingClientGetIceConfigInfoCout(): Signaling Client Get ICE Config Info Count
2019-12-07 01:53:57 VERBOSE signalingClientGetIceConfigInfo(): Signaling Client Get ICE Config Info
2019-12-07 01:53:57 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_NONE to ICE_AGENT_STATE_NEW
  • start the js viewer again, then the program will crash.
  • stacktrace:
* thread #8, stop reason = EXC_BAD_ACCESS (code=1, address=0x10)
  * frame #0: 0x0000000100101c8d libkvsWebrtcClient.dylib`onSctpOutboundPacket(addr=0x0000000000000000, data=0x0000000100731940, length=16, tos='\0', set_df='\0') at Sctp.c:150:5
    frame #1: 0x0000000100387dbc libusrsctp.1.dylib`sctp_send_resp_msg(src=0x000070000b992ba0, dst=0x000070000b992b90, sh=0x000000010073cf60, vtag=4152928290, type='\x06', cause=0x0000000000000000, vrf_id=0, port=0) at sctp_output.c:12021:10
    frame #2: 0x000000010037ab15 libusrsctp.1.dylib`sctp_send_abort(m=0x000000010073cf10, iphlen=0, src=0x000070000b992ba0, dst=0x000070000b992b90, sh=0x000000010073cf60, vtag=4152928290, cause=0x0000000000000000, vrf_id=0, port=0) at sctp_output.c:13091:2
    frame #3: 0x000000010035eae9 libusrsctp.1.dylib`sctp_common_input_processing(mm=0x000070000b992b88, iphlen=0, offset=12, length=100, src=0x000070000b992ba0, dst=0x000070000b992b90, sh=0x000000010073cf60, ch=0x000000010073cf6c, compute_crc='\x01', ecn_bits='\0', vrf_id=0, port=0) at sctp_input.c:5843:5
    frame #4: 0x00000001003f3a7e libusrsctp.1.dylib`usrsctp_conninput(addr=0x0000000000000000, buffer=0x00000001021a7040, length=100, ecn_bits='\0') at user_socket.c:3518:2
    frame #5: 0x0000000100101cf4 libkvsWebrtcClient.dylib`putSctpPacket(pSctpSession=0x0000000000000000, buf="\x13\x88\x13\x88", bufLen=100) at Sctp.c:160:5
    frame #6: 0x00000001000ee5ed libkvsWebrtcClient.dylib`onInboundPacket(customData=4329910272, buff="\x13\x88\x13\x88", buffLen=157) at PeerConnection.c:86:13
    frame #7: 0x00000001000decbf libkvsWebrtcClient.dylib`incomingDataHandler(customData=4311989248, pSocketConnection=0x00000001007259c0, pBuffer="\x13\x88\x13\x88", bufferLen=157, pSrc=0x000070000b992e70, pDest=0x0000000000000000) at IceAgent.c:1297:9
    frame #8: 0x00000001000dc263 libkvsWebrtcClient.dylib`connectionListenerReceiveDataRoutine(arg=0x00000001021a7000) at ConnectionListener.c:282:25
    frame #9: 0x00007fff7cb572eb libsystem_pthread.dylib`_pthread_body + 126
    frame #10: 0x00007fff7cb5a249 libsystem_pthread.dylib`_pthread_start + 66
    frame #11: 0x00007fff7cb5640d libsystem_pthread.dylib`thread_start + 13

Connection timed out

I successfully compiled on arm64, but am unable to run any of the three samples without a connection timeout.

:~/amazon-kinesis-video-streams-webrtc-sdk-c/build$ AWS_ACCESS_KEY_ID="access" AWS_SECRET_ACCESS_KEY="secret" REGION_NAME="us-west-2" ./kvsWebrtcClientMasterGstSample demo2
[KVS GStreamer Master] Using trickleICE by default
[KVS GStreamer Master] Created signaling channel demo2
[KVS Gstreamer Master] Finished initializing GStreamer
[KVS Gstreamer Master] Streaming video only
[KVS GStreamer Master] KVS WebRTC initialization completed successfully
[KVS GStreamer Master] Signaling client created successfully
[KVS GStreamer Master] Signaling client connection to socket established
[KVS Gstreamer Master] Beginning streaming...check the stream over channel demo2
2020-01-15 00:49:10 DEBUG   iceAgentValidateKvsRtcConfig(): 
	iceLocalCandidateGatheringTimeout: 10000 ms
	iceConnectionCheckTimeout: 10000 ms
	iceCandidateNominationTimeout: 10000 ms
	iceConnectionCheckPollingInterval: 50 ms
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client receive {"messagePayload":"[...snip...]","messageType":"ICE_CANDIDATE","senderClientId":"ik44sfhawixoqeq1zfu"}
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_NONE to ICE_AGENT_STATE_NEW.
2020-01-15 00:49:10 INFO    signalingClientSendMessageSync(): Signaling Client Sending Message Sync
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
 {"messagePayload":"[...snip...]","messageType":"ICE_CANDIDATE","senderClientId":"ik44sfhawixoqeq1zfu"}
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 DEBUG   stepStateMachine(): State Machine - Current state: 0x0000000000000001, Next state: 0x0000000000000002
2020-01-15 00:49:10 INFO    signalingClientSendMessageSync(): Signaling Client Sending Message Sync
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 INFO    signalingClientSendMessageSync(): Signaling Client Sending Message Sync
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 INFO    signalingClientSendMessageSync(): Signaling Client Sending Message Sync
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client receive 
2020-01-15 00:49:10 WARN    receiveLwsMessage(): Signaling received an empty message
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client receive 
2020-01-15 00:49:10 WARN    receiveLwsMessage(): Signaling received an empty message
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client receive 
2020-01-15 00:49:10 WARN    receiveLwsMessage(): Signaling received an empty message
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client receive 
2020-01-15 00:49:10 WARN    receiveLwsMessage(): Signaling received an empty message
2020-01-15 00:49:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:20 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:30 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:40 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:49:50 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:50:00 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:50:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:50:20 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:50:30 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:50:40 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:50:50 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:51:00 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:51:10 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-15 00:51:17 WARN    createSocket(): connect() failed with errno Connection timed out
2020-01-15 00:51:17 ERROR   createSocketConnection(): operation returned status code: 0x5800001d
2020-01-15 00:51:17 ERROR   turnConnectionStepState(): operation returned status code: 0x5800001d
2020-01-15 00:51:17 DEBUG   turnConnectionStepState(): TurnConnection state changed from TURN_STATE_NEW to TURN_STATE_FAILED
2020-01-15 00:51:17 ERROR   turnConnectionStart(): operation returned status code: 0x5800001d
2020-01-15 00:51:17 ERROR   executeGatheringIceAgentState(): operation returned status code: 0x5800001d

My device has internet access, definitely reacts to the presence of an available client (such as the browser-viewer on the AWS console), but is never able to send data. The client also never detects a connection.

At first I wondered if it was a firewall issue, but the kvs examples do work on my desktop machine, which is behind the same firewall.

I have also tested that gstreamer is working correctly on my arm64 device, as I can create a regular RTP video stream from it to my desktop (on the same LAN).

Any tips? I am not quite sure how to interpret the console log.

Thanks!

Validate input media

We should explore adding some basic input validation for H264/VP8/Opus. Full validation isn't needed, but just enough to assert that the bitstream looks ok.

Maybe this should be a debug only feature? On constrained devices this might be costly.

Allow user greater control during certificate generation.

It took at least 5s to generate key with 2048 bits, is there any problem if I use 1024? If I use 1024 it only takes about 1 second. This will help me to preview the video faster.

GCC/4.6.1 Linux/3.4.43-gk armv6l

10:10:42  Jiang createCertificateAndKey RSA_generate_key_ex[97]
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 8
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client receive {"messagePayload":"eyJjYW5kaWRhdGUiOiJjYW5kaWRhdGU6MzQwMjEzMDIyMiAxIHVkcCAzMzU2MjYyMyAzLjIzMS40Ljk5IDUxNjc0IHR5cCByZWxheSByYWRkciAxMTguMTkxLjIyNC4xNTEgcnBvcnQgMTM3NTYgZ2VuZXJhdGlvbiAwIHVmcmFnIERQa2cgbmV0d29yay1jb3N0IDk5OSIsInNkcE1pZCI6IjAiLCJzZHBNTGluZUluZGV4IjowfQ==","messageType":"ICE_CANDIDATE","senderClientId":"danspehvserjxl01kuledj"}
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 10
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client is writable
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 8
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client receive {"messagePayload":"eyJjYW5kaWRhdGUiOiJjYW5kaWRhdGU6MzQwMjEzMDIyMiAxIHVkcCAzMzU2MjYyMyAzLjIzMS40Ljk5IDQ5OTk1IHR5cCByZWxheSByYWRkciAxMTguMTkxLjIyNC4xNTEgcnBvcnQgMTM3NTggZ2VuZXJhdGlvbiAwIHVmcmFnIERQa2cgbmV0d29yay1jb3N0IDk5OSIsInNkcE1pZCI6IjEiLCJzZHBNTGluZUluZGV4IjoxfQ==","messageType":"ICE_CANDIDATE","senderClientId":"danspehvserjxl01kuledj"}
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 10
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client is writable
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 8
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client receive {"messagePayload":"eyJjYW5kaWRhdGUiOiJjYW5kaWRhdGU6MzM2OTI2NjI2MyAxIHVkcCAzMzU2MjM2NyAzLjIwOC4zMC4xOTggNTcxODQgdHlwIHJlbGF5IHJhZGRyIDExOC4xOTEuMjI0LjE1MSBycG9ydCAxMzc1NyBnZW5lcmF0aW9uIDAgdWZyYWcgRFBrZyBuZXR3b3JrLWNvc3QgOTk5Iiwic2RwTWlkIjoiMSIsInNkcE1MaW5lSW5kZXgiOjF9","messageType":"ICE_CANDIDATE","senderClientId":"danspehvserjxl01kuledj"}
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 10
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client is writable
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 8
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client receive {"messagePayload":"eyJjYW5kaWRhdGUiOiJjYW5kaWRhdGU6MzM2OTI2NjI2MyAxIHVkcCAzMzU2MjM2NyAzLjIwOC4zMC4xOTggNTU3ODUgdHlwIHJlbGF5IHJhZGRyIDExOC4xOTEuMjI0LjE1MSBycG9ydCAxMzc1NSBnZW5lcmF0aW9uIDAgdWZyYWcgRFBrZyBuZXR3b3JrLWNvc3QgOTk5Iiwic2RwTWlkIjoiMCIsInNkcE1MaW5lSW5kZXgiOjB9","messageType":"ICE_CANDIDATE","senderClientId":"danspehvserjxl01kuledj"}
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): WSS callback with reason 10
10:10:42  2019-12-28 02:10:38 VERBOSE lwsWssCallbackRoutine(): Client is writable
10:10:44  
10:10:44  
10:10:47  Jiang createCertificateAndKey RSA_generate_key_ex[99]
10:10:47  2019-12-28 02:10:43 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_NONE to ICE_AGENT_STATE_NEW.

No package 'libsrtp2' found

I am following in devguide and get an error during the cmake .. step

~/aws2/amazon-kinesis-video-streams-webrtc-sdk-c/build$ cmake ..
-- Kinesis Video PIC path is /home/myuser/aws2/amazon-kinesis-video-streams-webrtc-sdk-c/open-source/amazon-kinesis-video-streams-producer-sdk-cpp/kinesis-video-pic/
-- Kinesis Video C Producer path is /home/myuser/aws2/amazon-kinesis-video-streams-webrtc-sdk-c/open-source/amazon-kinesis-video-streams-producer-sdk-cpp/kinesis-video-c-producer/
-- Kinesis Video WebRTC Client path is /home/myuser/aws2/amazon-kinesis-video-streams-webrtc-sdk-c
-- dependencies install path is /home/myuser/aws2/amazon-kinesis-video-streams-webrtc-sdk-c/open-source/local
-- Bitness 64 bits
-- Checking for module 'libsrtp2'
--   No package 'libsrtp2' found
CMake Error at /usr/share/cmake-3.13/Modules/FindPkgConfig.cmake:452 (message):
  A required package was not found
Call Stack (most recent call first):
  /usr/share/cmake-3.13/Modules/FindPkgConfig.cmake:622 (_pkg_check_modules_internal)
  CMakeLists.txt:308 (pkg_check_modules)


-- Configuring incomplete, errors occurred!
See also "/home/myuser/aws2/amazon-kinesis-video-streams-webrtc-sdk-c/build/CMakeFiles/CMakeOutput.log".
See also "/home/myuser/aws2/amazon-kinesis-video-streams-webrtc-sdk-c/build/CMakeFiles/CMakeError.log".

This happens on an arm64 machine running Ubuntu Xenial 16.04. I did not have this problem on my laptop running 16.04, so I assume it is either arm64 related, or something wrong with my machine's configuration.

I'll keep digging, but any suggestions would be appreciated. I was assuming that these dependencies are built from source rather than installed, so I am surprised that it can't find libsrtp.

signaling channel crash

Websocket is not properly established. singaling channel code tried again, and then segfault.
Backtracce is as the following:

2020-01-15 00:06:46 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000001, Next state: 0x0000000000000002
2020-01-15 00:06:46 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000002, Next state: 0x0000000000000004
2020-01-15 00:06:47 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000004, Next state: 0x0000000000000010
2020-01-15 00:06:47 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000010, Next state: 0x0000000000000020
2020-01-15 00:06:48 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000020, Next state: 0x0000000000000040
2020-01-15 00:06:48 INFO    signalingClientConnectSync(): Signaling Client Connect Sync
2020-01-15 00:06:48 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000040, Next state: 0x0000000000000080
2020-01-15 00:06:53 ERROR   connectSignalingChannelLws(): operation returned status code: 0x0000000f
2020-01-15 00:06:53 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000080, Next state: 0x0000000000000004
2020-01-15 00:06:53 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000004, Next state: 0x0000000000000010
2020-01-15 00:06:54 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000010, Next state: 0x0000000000000020
2020-01-15 00:06:55 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000020, Next state: 0x0000000000000040
2020-01-15 00:06:55 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000040, Next state: 0x0000000000000080
2020-01-15 00:06:55 WARN    lwsWssCallbackRoutine(): Client connection failed. Connection error string: closed before established
2020-01-15 00:06:56 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000080, Next state: 0x0000000000000004
2020-01-15 00:06:57 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000004, Next state: 0x0000000000000010
2020-01-15 00:06:57 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000010, Next state: 0x0000000000000020
2020-01-15 00:06:58 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000020, Next state: 0x0000000000000040
2020-01-15 00:06:58 INFO    stepStateMachine(): State Machine - Current state: 0x0000000000000040, Next state: 0x0000000000000080
./webrtc(_Z15segsegv_handleri+0x4a)[0x5649f3a456da]
/lib/x86_64-linux-gnu/libc.so.6(+0x3ef20)[0x7f7eb88cef20]
./libkvsWebrtcSignalingClient.so(lwsWssCallbackRoutine+0xe2)[0x7f7eb9bf4c7d]
/home/weizhang/git/kvs-x86/open-source/local/lib/libwebsockets.so.15(+0x111a8)[0x7f7eb7ad71a8]
/home/weizhang/git/kvs-x86/open-source/local/lib/libwebsockets.so.15(+0x1581f)[0x7f7eb7adb81f]
/home/weizhang/git/kvs-x86/open-source/local/lib/libwebsockets.so.15(+0x2b6e3)[0x7f7eb7af16e3]
/home/weizhang/git/kvs-x86/open-source/local/lib/libwebsockets.so.15(lws_service+0x45)[0x7f7eb7adb675]
./libkvsWebrtcSignalingClient.so(lwsCompleteSync+0x4c3)[0x7f7eb9bf5a4c]
./libkvsWebrtcSignalingClient.so(lwsListenerHandler+0xdc)[0x7f7eb9bf8b0d]
/lib/x86_64-linux-gnu/libpthread.so.0(+0x76db)[0x7f7eb97cf6db]

Can we store the streamed videos?

Hi,

Are the videos stored anywhere (as in normal KVS)? Can we access the previously streamed video using something like GetMedia or HLS Session?

I am able to stream using Raspberry Pi and Mac and able to view only when the session is active.

Allow MTU to be configured by user

We should think about the API looks like, but we should allow the user to configure the MTU if they want.

Some users will be in constrained environments, and they know best the setup that works for them.

(BUG) CHK_WARN CHK_ERR should not be inside MUTEX_LOCK

There are many case where CHK_WARN or CHK_ERR or CKH_STATUS are inside a MUTEX_LOCK block, which would skip the mutex unlock when error occurs.

Such as : https://github.com/awslabs/amazon-kinesis-video-streams-webrtc-sdk-c/blob/master/samples/Common.c#L109 AND https://github.com/awslabs/amazon-kinesis-video-streams-webrtc-sdk-c/blob/master/samples/Common.c#L114

The CHK_WARN, CHK_ERR just use a goto cleanup when error occurs, and will not unlock the mutex.

Pls make some test cases and polish the code.

Support non-rsize RTCP

Currently when we parse RTCP we only look at the first in the compound packet. Because of this NACKs only work with clients that support (breaking FireFox)

Use non-blocking socket

If I read the code correcly. FIONBIO (non-blocking socket) was not used.
So during writeFrame in https://github.com/awslabs/amazon-kinesis-video-streams-webrtc-sdk-c/blob/master/samples/kvsWebRTCClientMaster.c#L192
And the underlying layer simply called send.
If only one client network connection was blocked, it will blocked all other clients, since the sample use a simple for-loop calling writeFrame to all connected clients and the underlying layer does not use non-blocking socket.

It will makes all clients have videos degraded if only one client had bad network connection.

ICE connection succeeded but TURN connection timed out causing continuous printing

Reconnect successfully after ICE connection timeout , it is still printing as follows before disconnecting.

2019-12-19 12:56:40 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:40 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   onIceCandidateHandler(): ice candidate gathering finished
2019-12-19 12:56:41 DEBUG   stepStateMachine(): State Machine - Current state: 0x0000000000000002, Next state: 0x0000000000000004
2019-12-19 12:56:41 DEBUG   executeCheckConnectionIceAgentState(): ice candidate pair count 18
2019-12-19 12:56:41 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_GATHERING to ICE_AGENT_STATE_CHECK_CONNECTION.
2019-12-19 12:56:41 DEBUG   onConnectionStateChange(): New connection state 2
2019-12-19 12:56:41 DEBUG   handleStunPacket(): local candidate ip address does not match with xor mapped address in binding response
2019-12-19 12:56:41 DEBUG   iceAgentCheckPeerReflexiveCandidate(): New local peer reflexive candidate found
2019-12-19 12:56:41 DEBUG   handleStunPacket(): received candidate with USE_CANDIDATE flag, local candidate type prflx.
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   stepStateMachine(): State Machine - Current state: 0x0000000000000004, Next state: 0x0000000000000008
2019-12-19 12:56:41 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_CHECK_CONNECTION to ICE_AGENT_STATE_CONNECTED.
2019-12-19 12:56:41 DEBUG   onConnectionStateChange(): New connection state 3
2019-12-19 12:56:41 DEBUG   stepStateMachine(): State Machine - Current state: 0x0000000000000008, Next state: 0x0000000000000020
2019-12-19 12:56:41 DEBUG   executeReadyIceAgentState(): Selected pair ip address: 192.168.2.106, port 59692, local candidate type: prflx
2019-12-19 12:56:41 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_CONNECTED to ICE_AGENT_STATE_READY.
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:41 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:42 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020
2019-12-19 12:56:42 DEBUG   turnConnectionStepState(): TurnConnection in TURN_STATE_FAILED due to 0x5a000020

Build error on macOS

My attempt to build the SDK on mac failed with an error.

  • Repo rev: 59236d7
  • XCode version: 11.3, Build version 11C29

The error log:

$ make
 :
[ 60%] Linking C shared library libkvsWebrtcSignalingClient.dylib
ld: warning: ignoring file ../open-source/local/lib/libjsmn.a, building for macOS-x86_64 but attempting to link with file built for macOS-x86_64
Undefined symbols for architecture x86_64:
  "_jsmn_init", referenced from:
      _receiveLwsMessage in LwsApiCalls.c.o
      _describeChannelLws in LwsApiCalls.c.o
      _createChannelLws in LwsApiCalls.c.o
      _getChannelEndpointLws in LwsApiCalls.c.o
      _getIceConfigLws in LwsApiCalls.c.o
  "_jsmn_parse", referenced from:
      _receiveLwsMessage in LwsApiCalls.c.o
      _describeChannelLws in LwsApiCalls.c.o
      _createChannelLws in LwsApiCalls.c.o
      _getChannelEndpointLws in LwsApiCalls.c.o
      _getIceConfigLws in LwsApiCalls.c.o
ld: symbol(s) not found for architecture x86_64
clang: error: linker command failed with exit code 1 (use -v to see invocation)
make[2]: *** [libkvsWebrtcSignalingClient.dylib] Error 1
make[1]: *** [CMakeFiles/kvsWebrtcSignalingClient.dir/all] Error 2
make: *** [all] Error 2

What I did:

git clone --recursive [email protected]:awslabs/amazon-kinesis-video-streams-webrtc-sdk-c.git
cd amazon-kinesis-video-streams-webrtc-sdk-c
mkdir -p build
cd build
cmake ..
make

Implement congestion control

We should then emit feedback back to the user so they can interact with their encoder.

We should also update the GStreamer sample to send events to the pipeline with bitrate suggestions.

Cross-compile build in docker

Hi! I have simple Dockerfile with arm toolchain

FROM debian

RUN DEBIAN_FRONTEND=noninteractive apt-get update && apt-get -y install \
    build-essential cmake gawk libncurses-dev libc6-dev intltool python \
    git subversion time unzip zlib1g-dev libssl-dev wget curl cpio bc \
    gettext gettext-base liblocale-gettext-perl upx \
    flex texinfo help2man libtool-bin byacc bison pkg-config libyaml-dev

WORKDIR /root/
RUN git clone https://github.com/crosstool-ng/crosstool-ng
WORKDIR /root/crosstool-ng
RUN ./bootstrap
RUN ./configure && make && make install 
RUN ct-ng arm-unknown-linux-uclibcgnueabi
RUN ct-ng build

# Now we have toolchain in /root/x-tools/arm-unknown-linux-uclibcgnueabi/

# git clone or copy aws_webrtc repo
COPY ./aws_webrtc /src/aws_webrtc
WORKDIR /src/aws_webrtc

# How can i start cmake to build aws webrtc with my own toolchain?

I tried to set ENV

ENV TARGET arm-unknown-linux-uclibcgnueabi
ENV CC /root/x-tools/arm-unknown-linux-uclibcgnueabi/bin/arm-unknown-linux-uclibcgnueabi-gcc
ENV AR /root/x-tools/arm-unknown-linux-uclibcgnueabi/bin/arm-unknown-linux-uclibcgnueabi-ar

but cmake can't to build openssl. It is trying to set -m64 for arm-unknown-linux-uclibcgnueabi-gcc

Can you explain how to build AWS webrtc inside a docker container?
Maybe i need to do it with a different way?
Thanks!

can't resolve symbol 'HMAC_CTX_new' (linux-mips32)

Hi, I cross-compiled the program and run on linux-mips32 platform , then I got ./kvsWebrtcClientMaster: can't resolve symbol 'HMAC_CTX_new'.
I search the code related to "HMAC_CTX_new" , only find -DLWS_HAVE_HMAC_CTX_new=1 in libwebsockets-CMakeLists.txt . And google given little information.
May I kown the definition's effect ? And how can I handle it ?
Best Regards and Merry Christmas !

Enable MSAN

  • MSAN we need to build all libraries instrumented.

Signalling Reconnection Failure

Steps to repro

  • start kvsWebrtcClientMaster sample, but dont start any viewer
  • wait for 5 min. After around 5min, there should be log showing signaling tries to refresh iceServers.
  • Start the viewer
    • expected outcome: master receives the offer and starts streaming
    • actual outcome: master doesnt receive anything.

print success messages in samples, unrelated to logging levels

So users know that things are working we should print success messages directly in the samples.

If they wish to delete those lines they can delete them from their code, but they shouldn't be controlled by logging levels so they are always printed. We want to have very minimal console spew (just success messages) in the default case.

Enable all compiler warnings

Currently unable to build. These are all the blocking issues.

  • Remove -Wgnu-zero-variadic-macro-arguments suppression from Include_i.h

Packet dropped by kernel silently

Hi, I encountered packet drop issue on my Ubuntu 18.04 machine, which turned out be network config problem, my solution was sysctl -w net.core.rmem_default=262144 to increase the socket buffer size. In real life, the I frame could be pretty big, I am thinking maybe the software should check and increase the kernel socket buffer size, to avoid weird and unnecessary packet drops, please comment.

The status is ICE_AGENT_STATE_READY, but the web test page has no images

HI:

I'm using the aws-sdk-kvs /2.1.0 migration to the MIPS platform.

The output information of Internet of things devices is as follows:

2020-01-07 10:13:46 DEBUG   turnConnectionStepState(): TurnConnection state changed from TURN_STATE_BIND_CHANNEL to TURN_STATE_READY
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   turnConnectionHandleChannelDataTcpMode(): operation returned status code: 0x5a000024
2020-01-07 10:13:46 DEBUG   turnConnectionIncomingDataHandler(): operation returned status code: 0x5a000024
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   turnConnectionHandleChannelDataTcpMode(): operation returned status code: 0x5a000024
2020-01-07 10:13:46 DEBUG   turnConnectionIncomingDataHandler(): operation returned status code: 0x5a000024
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   handleStunPacket(): Dropping response packet because transaction id does not match
2020-01-07 10:13:46 DEBUG   stepStateMachine(): State Machine - Current state: 0x0000000000000004, Next state: 0x0000000000000008
2020-01-07 10:13:46 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_CHECK_CONNECTION to ICE_AGENT_STATE_CONNECTED.
2020-01-07 10:13:46 DEBUG   onConnectionStateChange(): New connection state 3
2020-01-07 10:13:46 DEBUG   stepStateMachine(): State Machine - Current state: 0x0000000000000008, Next state: 0x0000000000000020
2020-01-07 10:13:46 DEBUG   executeReadyIceAgentState(): Selected pair ip address: 34.215.13.39, port 65470, local candidate type: relay
2020-01-07 10:13:46 DEBUG   stepIceAgentStateMachine(): Ice agent state changed from ICE_AGENT_STATE_CONNECTED to ICE_AGENT_STATE_READY.
2020-01-07 10:13:51 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:14:01 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:14:11 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:14:22 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:14:33 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:14:43 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:14:54 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:15:04 DEBUG   lwsWssCallbackRoutine(): Client is writable
2020-01-07 10:15:15 DEBUG   lwsWssCallbackRoutine(): Client is writable

mips_0x0000000f_20200107.txt

mips_ICE_AGENT_STATE_READY_20200107.txt

The usage method is the same as Ubuntu, using the resource file h264SampleFrames&opusSampleFrames that comes with the SDK

What is the cause of this, thank you!

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.