Code Monkey home page Code Monkey logo

link's Introduction

Ableton Link

This is the codebase for Ableton Link, a technology that synchronizes musical beat, tempo, and phase across multiple applications running on one or more devices. Applications on devices connected to a local network discover each other automatically and form a musical session in which each participant can perform independently: anyone can start or stop while still staying in time. Anyone can change the tempo, the others will follow. Anyone can join or leave without disrupting the session.

License

Ableton Link is dual licensed under GPLv2+ and a proprietary license. If you would like to incorporate Link into a proprietary software application, please contact [email protected].

Building and Running Link Examples

Link relies on asio-standalone as a submodule. After checking out the main repositories, those submodules have to be loaded using

git submodule update --init --recursive

Link uses CMake to generate build files for the Catch-based unit-tests and the example applications.

$ mkdir build
$ cd build
$ cmake ..
$ cmake --build .

The output binaries for the example applications and the unit-tests will be placed in a bin subdirectory of the CMake binary directory.

Integrating Link in your Application

Test Plan

To make sure users have the best possible experience using Link it is important all apps supporting Link behave consistently. This includes for example playing in sync with other apps as well as not hijacking a jams tempo when joining. To make sure your app behaves as intended make sure it complies to the Test Plan.

Building Link

Link is a header-only library, so it should be straightforward to integrate into your application.

CMake-based Projects

If you are using CMake, then you can simply add the following to your CMakeLists.txt file:

include($PATH_TO_LINK/AbletonLinkConfig.cmake)
target_link_libraries($YOUR_TARGET Ableton::Link)

You can optionally have your build target depend on ${link_HEADERS}, which will make the Link headers visible in your IDE. This variable exported to the PARENT_SCOPE by Link's CMakeLists.txt.

Other Build Systems

To include the Link library in your non CMake project, you must do the following:

  • Add the link/include and modules/asio-standalone/asio/include directories to your list of include paths
  • Define LINK_PLATFORM_MACOSX=1, LINK_PLATFORM_LINUX=1, or LINK_PLATFORM_WINDOWS=1, depending on which platform you are building on.

If you get any compiler errors/warnings, have a look at compile-flags.cmake, which might provide some insight as to the compiler flags needed to build Link.

Build Requirements

Platform Minimum Required Optional (only required for examples)
Windows MSVC 2015 Steinberg ASIO SDK 2.3
Mac Xcode 9.4.1
Linux Clang 3.6 or GCC 5.2 libportaudio19-dev

Other compilers with good C++11 support should work, but are not verified.

iOS developers should not use this repo. See http://ableton.github.io/linkkit for information on the LinkKit SDK for iOS.

Documentation

An overview of Link concepts can be found at http://ableton.github.io/link. Those that are new to Link should start there. The Link.hpp header contains the full Link public interface. See the LinkHut projects in this repo for an example usage of the Link type.

Time and Clocks

Link works by calculating a relationship between the system clocks of devices in a session. Since the mechanism for obtaining a system time value and the unit of these values differ across platforms, Link defines a Clock abstraction with platform-specific implementations. Please see:

Using the system time correctly in the context of an audio callback gets a little complicated. Audio devices generally have a sample clock that is independent of the system Clock. Link maintains a mapping between system time and beat time and therefore can't use the sample time provided by the audio system directly.

On OSX and iOS, the CoreAudio render callback is passed an AudioTimeStamp structure with a mHostTime member that represents the system time at which the audio buffer will be passed to the audio hardware. This is precisely the information needed to derive the beat time values corresponding to samples in the buffer using Link. Unfortunately, not all platforms provide this data to the audio callback.

When a system timestamp is not provided with the audio buffer, the best a client can do in the audio callback is to get the current system time and filter it based on the provided sample time. Filtering is necessary because the audio callback will not be invoked at a perfectly regular interval and therefore the queried system time will exhibit jitter relative to the sample clock. The Link library provides a HostTimeFilter utility class that performs a linear regression between system time and sample time in order to improve the accuracy of system time values used in an audio callback. See the audio callback implementations for the various platforms used in the examples to see how this is used in practice. Note that for Windows-based systems, we recommend using the ASIO audio driver.

Latency Compensation

As discussed in the previous section, the system time that a client is provided in an audio callback either represents the time at which the buffer will be submitted to the audio hardware (for OSX/iOS) or the time at which the callback was invoked (when the code in the callback queries the system time). Note that neither of these is what we actually want to synchronize between devices in order to play in time.

In order for multiple devices to play in time, we need to synchronize the moment at which their signals hit the speaker or output cable. If this compensation is not performed, the output signals from devices with different output latencies will exhibit a persistent offset from each other. For this reason, the audio system's output latency should be added to system time values before passing them to Link methods. Examples of this latency compensation can be found in the platform implementations of the example apps.

link's People

Contributors

abique avatar ala-ableton avatar arximboldi avatar aza-ableton avatar brs-ableton avatar cdi-ableton avatar cox2 avatar csd-ableton avatar dewb avatar dir-ableton avatar fgo-ableton avatar hack3ric avatar llloret avatar mathiasbredholt avatar nre-ableton avatar nwu-ableton avatar ryb-ableton avatar timblechmann avatar umlaeute 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  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

link's Issues

Android test app

Hi,
I started a test app on Android. The (not yet fulfilled) goal is to have some springboard code similar to LinkHut, on Android platforms. Hopefully it can help others working on Android. Feedback is welcome, and contributions even more so!

https://github.com/jbloit/AndroidLinkAudio

Handling phase

One thing that I thought would be in the Link spec is a callback when a new bar was started. As it is, it seems as though it's up to us to poll this information and calculate when this has happened.

Is there any reason why this callback wasn't in the spec? thx

Tempo changes with large latency compensation values

I'm working on Link integration for SuperCollider. (Another developer, smiarx, did most of the work; I'm fixing up latency compensation and a couple of other issues.)

I'm struggling with the interaction between tempo changes and latency compensation.

Here's a test scenario.

  • Peer 1: Tempo = 60, for argument's sake assume initially that beats == seconds, latency 250 ms.
  • Peer 2: Tempo = 60, assume initially that beats == seconds, latency 100 ms.
Sec P1 beats P2 beats Event
9.75 10 9.85 P1: Note on
9.78 10.03 9.88 P2: Tempo change to 160
(x) 10.1 9.95 P1: Note off

(Sec and P1/P2 beats might look a little strange. In SC, the client-side clock needs to run earlier than the audio. Then, a latency offset is added to the OSC bundle timestamp so that the audio hits the wire at "now" [logical time] + latency. Secs 9.75 + latency 0.25 = hear it at 10.0 secs. In practice, on my Linux box, SC seems to need a minimum of 0.07 or 0.08 seconds OSC messaging latency.)

In theory, after the tempo change, the timeline's timeOrigin should correspond to 9.78 seconds -- therefore (x) should be 0.07 beats * secsPerBeat + timeOrigin = 0.07 * 3/8 + 9.78 = 9.80625.

I'm finding in practice that the link timeline is calculating a seconds value for the note-off that is exactly 100 ms before the note-on (???!!!), leaving a stuck note.

latency 0.25	SysClock logical time 77.10222	thisThread's logical time 49.0
	[ 9, 'default', 1004, 0, 1, 'out', 0, 'freq', 261.6255653006, 'amp', 0.1, 'pan', -1 ]

latency 0.25	SysClock logical time 77.00222	thisThread's logical time 49.1
	[ 15, 1004, 'gate', 0 ]

FAILURE IN SERVER /n_set Node 1004 not found
  • Should be: note-on 77.10222, note-off 77.15847
  • Is: note-on 77.10222, note-off 77.00222

P2 sets the tempo like this -- is this correct?

void LinkClock::SetTempoAtBeat(double inTempo, double inBeats)
{
	auto timeline = mLink.captureAppTimeline();
	// secs should subtract mLatency here
	// I'd rather do timeAtBeat() - mLatency,
	// but I haven't found the right answer at stackexchange yet
	auto time = timeline.timeAtBeat(inBeats - (mLatency * mTempo), mQuantum);
	timeline.setTempo(inTempo*60., time);

	mTempo = inTempo;
	mBeatDur = 1. / inTempo;

	mLink.commitAppTimeline(timeline);
	mCondition.notify_one();
}

In theory, inBeats should be 9.88, mLatency = 0.1, mTempo = 1, so timeAtBeat should be returning the value for 9.78, and I would expect, then, that the timeline's timeOrigin should match.

And P1 receives the tempo via a callback. Here, we should probably get secs from the timeline. But beats is used only for a callback into the SC language -- it isn't used to modify the timeline's state, so it shouldn't matter for this test case.

	mLink.setTempoCallback([this](double bpm) {
		double secs = elapsedTime();
		double tempo = bpm / 60.;

		auto timeline = mLink.captureAppTimeline();
		// I am not sure if `+ latency` is right here
		double beats = timeline.beatAtTime(hrToLinkTime(secs + mLatency), mQuantum);

		mTempo = tempo;
		mBeatDur = 1. / tempo;
		mCondition.notify_one();

		... SC-specific callback, doesn't affect audio...
	});

So... what am I doing wrong?

TIA.

Revision bbb6aa83c3ad5026e2da56a63e3047f5a01f6a41 seems to be broken (on Linux?)

Hi,

link examples were unstable for me on Linux.

I compiled the master branch of Link and built it in release mode.
Every tests passes.

Then I opened two terminals on the same computer, both using jack for the audio output.
Then I started LinkHut twice and let it play for a few minutes, clicks where on time, then I started to increase and decrease the tempo and at some point one of the LinkHut stopped to play.

Is it a known issue?

Alex.

fails to compile on non-linux UNIX

with #18 kind-of-resolved (haven't tested 31a8e4e but disabled the -m64 compiler flags myself), there are still some problems with compiling Link on more exotic flavors of UN*X, at least Debian/kFreeBSD and Debian/hurd

please see Debian#842653 for more information. (this is with 1.0.0, but I haven't seen any changes to the code in current HEAD that would suggest a fix)

Latency Compensation

Hi, I'm struggling to deal with how latency compensation is handled. Say Live is running and is Link enabled and has a total latency of 1s before a sound hits the speaker from the beat. My Link enabled app has a latency of 500ms from the beat. How do I know that I should wait an additional 500ms so that the sounds from Live are output at the same time as mine?

thx

Add some Peer infos

Is it planned to add some more info about connected peers ?
(like their name, IP, ... whatever info they want to expose)

I would like to broadcast some more info between our mac and iOS app. It should be great to use link discovery to do that.

Manual clock offset please

A manual offset of the synchronization would be very helpful in the protocol as a standard feature.

I'll try to explain my dj setup:

I use a Motu AVB audio interface which allows internal routing of 128 inputs and 128 outputs to be virtually connected in a matrix to either hardware I/O or to other virtual channels.

The way I'm using it is by linking the virtual I/O together.

In Traktor have separate outputs for each deck, so that's 4 stereo channels.
These channels are used in Ableton Live as live inputs, works flawlessly. There's a lot of DSP on the channels as well. In addition, I use Maschine as a vst plugin in Ableton as well with separate outputs for each group.

I sync Ableton and Traktor thru link. There is a slight delay because of the audio loopback from Traktor, approximately 8 ms. I just delay Maschine by 8 ms as well using track delay and all is solid.

However, if I then use link with other people, who are not delaying their audio i'll never get into sync.

If it were just a live set with no live audio inputs it wouldn't be a problem, the you could just give a negative track delay on the master channel. However you can't negative delay live incoming audio ;)

So by implementing a way to manually offset the clock received and sent by Link, a lot more would be possible...

I really hope someone can look into this, because it doesn't seem like difficult thing to do, but maybe you're just not aware of use cases like these..

Best regards.

Ruben

Novice computer science student looking to contribute

Hello everyone! How are you? I'm a Computer Science student and Ableton lover. I would really like to contribute to Link now that it is open source. However, I am not really sure where to begin. Does anyone have any tips on how to contribute or what exactly to do?

My apologies if this is kind of a redundant question. I was more so looking for tips from the direct people who are contributing rather than a vague article.

Thank you,
Besart

Using MSVC

Hi,
I'm trying to build a Cinder block for the Cinder Framework users here: https://github.com/brucelane/Cinder-AbletonLink
I'm using Visual Studio 2013 or 2015.
I added git submodules to get link, catch, asio repositories.
I added the preprocessor flags from the CMake file.
I don't understand how to fix error C2371 'asio::io_service' : redefinition; different basic types on this line.
Thank you for your help

Ableton Link + Unreal Engine

heyo, has anyone tried making or heard of an Ableton Link plugin for Unreal Engine 4? seems doable as they're both in C++

Second peer syncing to half beats?

I'm working on Link integration for SuperCollider.

I find occasionally, for no reason I can determine, that the second peer occasionally locks onto the "and-of" beat -- if the first peer is at beat 20.0, the second peer may be at 15.5.

Why would this be?

is there a way to use Quantum without AudioEngine?

as i am writing Quartz Composer API implementation came around the need of Quantum setting without the use of AudioEngine.
Quartz Composer Compositions are basically producing visual content only controlled in three different time spaces (none, idle, extern/local) with an macro traversing engine. So its similar to pureData or maxmsp but not same.
So could rewrite code using EngineData structure without Audiobuffers but it would be easier when using the link without metronome but still make use of quantum setting apart from audioengine. Or i need a hint what i didnt see yet in AudioEngine.cpp.

fails to compile on Debian/stretch

for whatever reasons, Link fails to build from source on Debian stretch/sid amd64 as of today

$ mkdir build
$ cd build
$ cmake -DLINK_PLATFORM_LINUX=1  ..
$ cmake --build .
[...]
[ 53%] Building CXX object src/CMakeFiles/LinkCoreTest.dir/ableton/link/tst_LinearRegression.cpp.o
/tmp/zmoelnig/ableton-link/src/ableton/link/tst_LinearRegression.cpp: In function โ€˜void ableton::link::____C_A_T_C_H____T_E_S_T____39()โ€™:
/tmp/zmoelnig/ableton-link/src/ableton/link/tst_LinearRegression.cpp:43:14: error: ambiguous overload for โ€˜operator=โ€™ (operand types are โ€˜std::array<std::pair<double, double>, 1ul>::value_type {aka std::pair<double, double>}โ€™ and โ€˜<brace-enclosed initializer list>โ€™)
   data[0] = {};
              ^
In file included from /usr/include/c++/6/utility:70:0,
                 from /tmp/zmoelnig/ableton-link/include/ableton/link/LinearRegression.hpp:25,
                 from /tmp/zmoelnig/ableton-link/src/ableton/link/tst_LinearRegression.cpp:20:
/usr/include/c++/6/bits/stl_pair.h:359:7: note: candidate: std::pair<_T1, _T2>& std::pair<_T1, _T2>::operator=(typename std::conditional<std::__and_<std::is_copy_assignable<_Tp>, std::is_copy_assignable<_T2> >::value, const std::pair<_T1, _T2>&, const std::__nonesuch&>::type) [with _T1 = double; _T2 = double; typename std::conditional<std::__and_<std::is_copy_assignable<_Tp>, std::is_copy_assignable<_T2> >::value, const std::pair<_T1, _T2>&, const std::__nonesuch&>::type = const std::pair<double, double>&]
       operator=(typename conditional<
       ^~~~~~~~
/usr/include/c++/6/bits/stl_pair.h:370:7: note: candidate: std::pair<_T1, _T2>& std::pair<_T1, _T2>::operator=(typename std::conditional<std::__not_<std::__and_<std::is_copy_assignable<_Tp>, std::is_copy_assignable<_T2> > >::value, const std::pair<_T1, _T2>&, const std::__nonesuch&>::type) [with _T1 = double; _T2 = double; typename std::conditional<std::__not_<std::__and_<std::is_copy_assignable<_Tp>, std::is_copy_assignable<_T2> > >::value, const std::pair<_T1, _T2>&, const std::__nonesuch&>::type = const std::__nonesuch&] <deleted>
       operator=(typename conditional<
       ^~~~~~~~
/usr/include/c++/6/bits/stl_pair.h:376:7: note: candidate: std::pair<_T1, _T2>& std::pair<_T1, _T2>::operator=(typename std::conditional<std::__and_<std::is_move_assignable<_Tp>, std::is_move_assignable<_T2> >::value, std::pair<_T1, _T2>&&, std::__nonesuch&&>::type) [with _T1 = double; _T2 = double; typename std::conditional<std::__and_<std::is_move_assignable<_Tp>, std::is_move_assignable<_T2> >::value, std::pair<_T1, _T2>&&, std::__nonesuch&&>::type = std::pair<double, double>&&]
       operator=(typename conditional<
       ^~~~~~~~
src/CMakeFiles/LinkCoreTest.dir/build.make:182: recipe for target 'src/CMakeFiles/LinkCoreTest.dir/ableton/link/tst_LinearRegression.cpp.o' failed
make[2]: *** [src/CMakeFiles/LinkCoreTest.dir/ableton/link/tst_LinearRegression.cpp.o] Error 1
CMakeFiles/Makefile2:142: recipe for target 'src/CMakeFiles/LinkCoreTest.dir/all' failed
make[1]: *** [src/CMakeFiles/LinkCoreTest.dir/all] Error 2
Makefile:83: recipe for target 'all' failed
make: *** [all] Error 2

I tried with both stock compilers, but the result is the same:

$ g++ --version
g++ (Debian 6.2.0-7) 6.2.0 20161018
Copyright (C) 2016 Free Software Foundation, Inc.
This is free software; see the source for copying conditions.  There is NO
warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.

$ clang++ --version
clang version 3.8.1-12 (tags/RELEASE_381/final)
Target: x86_64-pc-linux-gnu
Thread model: posix
InstalledDir: /usr/bin

Additional dependencies required for Rasbpian

portaudio needs to be installed on pi - I've installed this on jessie and all works fine.

sudo apt-get install portaudio19-dev

For some reason there are dependency problems so the user will also need to install the jackaudio packages listed.

Link in "sleep mode" at some point between iPads ?

Hello,

I'm using 4 ipads (but I can reproduce with 2 iPads) each of them having Link running on different apps.
At launch, I can see all Links app running smoothly, but, randomly from 10 min to an hour, each iPad are disconnected from each other.
Wifi stills there, but the only thing to do is to cut the wifi on each iPad, relaunch it quickly, then Link is back between the 2 devices...

Link still works on each iPad, stays in sync with the apps running on them, but no more sync between the 2 iPads.

I guess it's not the router (dedicated Airport Extreme just for Link) I just have an option "IGMP" which is not activated, but activated doesn't change a thing, the iPads are set to never go into sleep mode...
DHCP is automatic, wifi channel automatic, 5ghz band only, hidden WPA 2 network.

As far as I understand, it seems "Link between iPads" is crashing at some point...
Does that sound familiar to anyone here ?

Thanks !

fails to compile on any unix-non64bit architecture

building the 1.0.0 release for Debian, we find that ableton-link fails to compile on all non-64bit architectures (and on some 64bit architectures as well):

architecture status
amd64 Installed
arm64 Build-Attempted
armel Build-Attempted
armhf Build-Attempted
i386 Build-Attempted
mips Build-Attempted
mips64el Build-Attempted
mipsel Build-Attempted
powerpc Build-Attempted
ppc64el Installed
s390x Installed
alpha Build-Attempted
hppa Build-Attempted
hurd-i386 Failed
kfreebsd-amd64 Build-Attempted
kfreebsd-i386 Build-Attempted
(m68k Needs-Build)
(powerpcspe Needs-Build)
(ppc64 Needs-Build)
(sh4 BD-Uninstallable)
sparc64 Installed
x32 Build-Attempted

Debian#642410 suggest that this is due to the default LINK_WORD_SIZE=64 and the resulting use of -m64.

So my main question is, why does the build require the -m64 (resp. -m32) flags by default? Shouldn't most compilers have sane defaults?

version GLIBCXX_3.4.21 not defined in file libstdc++.so.6 with link time reference

Also opened an issue on the libpd/abl_link repo: libpd/abl_link#13
The folks there suggested I open one here as well.

I'm running PD 0.47 on KXStudio (Linux) and am able to successfully get the abl_link~ external using deken (PD's package manager). However, when I try to instantiate an abl_link~ object, I get this error:

/path/to/mypdexternals/abl_link~/abl_link~.pd_linux: /path/to/mypdexternals/abl_link~/abl_link~.pd_linux: symbol _ZNKSt3_V214error_category10_M_messageB5cxx11Ei, version GLIBCXX_3.4.21 not defined in file libstdc++.so.6 with link time reference

A user over at libpd said "looks like the issue is due to differing versions of gcc. Your system is running an older version with a slightly older libc++. The answer seems to be to build with the following define: -D_GLIBCXX_USE_CXX11_ABI=0."

I think the solution to this is for the libpd/abl_link developer to recompile the external with that flag and upload it to deken, but I'm putting this here in case anybody else is having a similar issue.

Protocol documentation

Detailed documentation of the message types, structures and sequences would be invaluable to projects which can't use the library code directly.

error building app with link: class ableton::Linkโ€™ has no member named โ€˜captureAppTimelineโ€™

Hi.
I'm trying to build an extension for SuperCollider that brings Ableton Link features to it: LinkUGen
It worked when I did it about one year a go. Now I'm getting these error while building it with clang++:

/home/gilfuser/builds/LinkUGen/Link.cpp:99:28: error: โ€˜class ableton::Linkโ€™ has no member named โ€˜captureAudioSessionStateโ€™; did you mean โ€˜captureAudioTimelineโ€™?
     auto timeline = gLink->captureAudioSessionState();
                            ^~~~~~~~~~~~~~~~~~~~~~~~
                            captureAudioTimeline
/home/gilfuser/builds/LinkUGen/Link.cpp: In function โ€˜void LinkTempo_Ctor(LinkTempo*)โ€™:
/home/gilfuser/builds/LinkUGen/Link.cpp:127:34: error: โ€˜class ableton::Linkโ€™ has no member named โ€˜captureAudioSessionStateโ€™; did you mean โ€˜captureAudioTimelineโ€™?
     const auto timeline = gLink->captureAudioSessionState();
                                  ^~~~~~~~~~~~~~~~~~~~~~~~
                                  captureAudioTimeline
/home/gilfuser/builds/LinkUGen/Link.cpp: In function โ€˜void LinkTempo_next(LinkTempo*, int)โ€™:
/home/gilfuser/builds/LinkUGen/Link.cpp:136:28: error: โ€˜class ableton::Linkโ€™ has no member named โ€˜captureAudioSessionStateโ€™; did you mean โ€˜captureAudioTimelineโ€™?
     auto timeline = gLink->captureAudioSessionState();
                            ^~~~~~~~~~~~~~~~~~~~~~~~
                            captureAudioTimeline
/home/gilfuser/builds/LinkUGen/Link.cpp:138:12: error: โ€˜class ableton::Linkโ€™ has no member named โ€˜commitAudioSessionStateโ€™; did you mean โ€˜commitAudioTimelineโ€™?
     gLink->commitAudioSessionState(timeline);
            ^~~~~~~~~~~~~~~~~~~~~~~
            commitAudioTimeline

There's no clue on the LinkUGen side of what should I do.
Should I accept the suggestion in the error log and change captureAudioSessionState into captureAudioTimeline?

cheers,
Gil

Disable the app interface?

Hi,

In my use case, I don't need the app interface because I only use link from the audio thread.

Would there be any benefit in disabling the app interface?

I was thinking that it could be achieved by doing: #define LINK_DISABLE_APP_INTERFACE 1.

Thank you,
Alex.

Integrating Link with a project with higher mininum Windows version

One of the projects I work on is attempting to integrate the Link library into the codebase, and we're running into problems because the project requires Win API functions introduced in Vista, but the CMake config file for this project adds compile flags to compile for XP support.

A log of the build is here. CancelIoEx and SHGetKnownFolderPath are Vista API functions.

https://ci.appveyor.com/project/brianlheim/supercollider-mu8dk/build/305/job/98e3uw5u2upo93oo

From what I understand the flags are propagated from the AsioStandalone lib as configured in this cmake file: https://github.com/Ableton/link/blob/master/cmake_include/AsioStandaloneConfig.cmake

CMake is a bit confusing to us, so we're not sure if there's a way to get around this on our end or your end without changes to the code itself. Any guidance you can provide on how best to do this integration would be very much appreciated.

Thanks!

Crash in asio

Hi,

I have no steps to reproduce the following crash, I think it is a race condition.

Maybe you could try to update asio?

Alex.

=================================================================
==1239==ERROR: AddressSanitizer: stack-use-after-scope on address 0x7fffdbeee6e0 at pc 0x5555567440ed bp 0x7fffdbeee6b0 sp 0x7fffdbeee6a0
READ of size 8 at 0x7fffdbeee6e0 thread T443
    #0 0x5555567440ec in void asio::detail::op_queue_access::next<asio::detail::scheduler_operation, asio::detail::scheduler_operation>(asio::detail::scheduler_operation*&, asio::detail::scheduler_operation*) ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/op_queue.hpp:40
    #1 0x55555673cb2e in asio::detail::op_queue<asio::detail::scheduler_operation>::push(asio::detail::scheduler_operation*) ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/op_queue.hpp:106
    #2 0x5555567282b3 in asio::detail::epoll_reactor::descriptor_state::perform_io(unsigned int) ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/impl/epoll_reactor.ipp:670
    #3 0x55555672844c in asio::detail::epoll_reactor::descriptor_state::do_complete(void*, asio::detail::scheduler_operation*, std::error_code const&, unsigned long) ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/impl/epoll_reactor.ipp:693
    #4 0x555556722a56 in asio::detail::scheduler_operation::complete(void*, std::error_code const&, unsigned long) ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/scheduler_operation.hpp:39
    #5 0x55555672a3ea in asio::detail::scheduler::do_run_one(asio::detail::scoped_lock<asio::detail::posix_mutex>&, asio::detail::scheduler_thread_info&, std::error_code const&) ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/impl/scheduler.ipp:375
    #6 0x555556729662 in asio::detail::scheduler::run(std::error_code&) ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/impl/scheduler.ipp:146
    #7 0x55555672aece in asio::io_context::run() ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/impl/io_context.ipp:59
    #8 0x5555567577f0 in ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}::operator()(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler) const ../../../third-party/ableton-link/include/ableton/platforms/asio/Context.hpp:65
    #9 0x555556762c4b in void std::__invoke_impl<void, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}, asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(std::__invoke_other, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}&&, asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler&&) /usr/include/c++/7.1.1/bits/invoke.h:60
    #10 0x55555675e548 in std::__invoke_result<ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}, asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>::type std::__invoke<ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}, asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}&&, (std::__invoke_result&&)...) /usr/include/c++/7.1.1/bits/invoke.h:95
    #11 0x5555567fd49c in decltype (__invoke((_S_declval<0ul>)(), (_S_declval<1ul>)(), (_S_declval<2ul>)())) std::thread::_Invoker<std::tuple<ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}, asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler> >::_M_invoke<0ul, 1ul, 2ul>(std::_Index_tuple<0ul, 1ul, 2ul>) /usr/include/c++/7.1.1/thread:234
    #12 0x5555567fbf68 in std::thread::_Invoker<std::tuple<ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}, asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler> >::operator()() /usr/include/c++/7.1.1/thread:243
    #13 0x5555567fafef in std::thread::_State_impl<std::thread::_Invoker<std::tuple<ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog>::Context<ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler>(ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)::{lambda(asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler)#1}, asio::io_context&, ableton::link::Controller<std::function<void (unsigned long)>, std::function<void (ableton::link::Tempo)>, ableton::platforms::linux::Clock<4>, ableton::platforms::asio::Context<ableton::platforms::posix::ScanIpIfAddrs, ableton::util::NullLog> >::UdpSendExceptionHandler> > >::_M_run() /usr/include/c++/7.1.1/thread:186
    #14 0x555558d1612e in execute_native_thread_routine (/home/abique/develop/bitwig/alex-future/target/bin/debug/BitwigAudioEngine+0x37c212e)
    #15 0x7ffff4760048 in start_thread (/usr/lib/libpthread.so.0+0x7048)
    #16 0x7ffff44a0f0e in clone (/usr/lib/libc.so.6+0xedf0e)

Address 0x7fffdbeee6e0 is located in stack of thread T443
SUMMARY: AddressSanitizer: stack-use-after-scope ../../../third-party/ableton-link/modules/asio-standalone/asio/include/asio/detail/op_queue.hpp:40 in void asio::detail::op_queue_access::next<asio::detail::scheduler_operation, asio::detail::scheduler_operation>(asio::detail::scheduler_operation*&, asio::detail::scheduler_operation*)
Shadow bytes around the buggy address:
  0x10007b7d5c80: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x10007b7d5c90: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x10007b7d5ca0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x10007b7d5cb0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x10007b7d5cc0: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
=>0x10007b7d5cd0: 00 00 00 00 00 00 00 00 00 00 00 00[f8]00 00 00
  0x10007b7d5ce0: 00 00 00 00 f1 f1 f1 f1 00 00 f2 f2 f2 f2 f2 f2
  0x10007b7d5cf0: 00 00 00 00 f3 f3 f3 f3 00 00 00 00 00 00 00 00
  0x10007b7d5d00: 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00
  0x10007b7d5d10: 00 00 00 00 00 00 00 00 00 00 00 00 f1 f1 f1 f1
  0x10007b7d5d20: 00 00 00 f2 f2 f2 f2 f2 00 00 00 f2 00 00 00 00
Shadow byte legend (one shadow byte represents 8 application bytes):
  Addressable:           00
  Partially addressable: 01 02 03 04 05 06 07 
  Heap left redzone:       fa
  Freed heap region:       fd
  Stack left redzone:      f1
  Stack mid redzone:       f2
  Stack right redzone:     f3
  Stack after return:      f5
  Stack use after scope:   f8
  Global redzone:          f9
  Global init order:       f6
  Poisoned by user:        f7
  Container overflow:      fc
  Array cookie:            ac
  Intra object redzone:    bb
  ASan internal:           fe
  Left alloca redzone:     ca
  Right alloca redzone:    cb

Difficulty including Link

I am trying to follow the directions on how to build a project which embeds Link, and am running into some trouble. It is quite likely due to me simply not knowing what I am doing, as I have never previously used cmake, and have not used C++ since 1993โ€ฆ but as I am stuck, I hope you will humor me, and perhaps this can result in slightly more explicit instructions in the future.

I am trying to build a program which uses both Link and mongoose, an open-source networking library. I was able to get the basic mongoose proof-of-concept code working with cmake and using C++ to compile (even though mongoose itself is a C library), but as soon as I try adding the include for Link, compilation fails.

Here is the content of my CMakeLists.txt:

cmake_minimum_required(VERSION 3.0)
project(Carabiner)

set(CMAKE_RUNTIME_OUTPUT_DIRECTORY ${CMAKE_BINARY_DIR}/bin)

set(mongoose_HEADERS
  mongoose.h
)

set(mongoose_SOURCES
  mongoose.c
)

add_executable(Carabiner
  ${mongoose_HEADERS}
  ${mongoose_SOURCES}
  carabiner.cpp
)

include(~/git/link/AbletonLinkConfig.cmake)
target_link_libraries(Carabiner Ableton::Link)

And when I mkdir build, cd build, and cmake .., that seems to work just fine. And I can compile (using cmake --build .) and run my source code (below) just fine, as long as I omit the line which tries to include the Link header. But as soon as that line is present, compilation fails with the errors shown below the source. This is on Mac OS X 10.11.6. (And when I follow the directions to create the Link example programs within the Link repository itself, that also works fine. The problem only occurs when I try to use Link from my own project.) Thanks in advance for any help you might be able to offer.

Here is carabiner.cpp:

extern "C" {
  #include "mongoose.h"
}
#include <ableton/Link.hpp>

static void ev_handler(struct mg_connection *nc, int ev, void *p) {
  struct mbuf *io = &nc->recv_mbuf;
  (void) p;
  switch (ev) {
    case MG_EV_RECV:
      mg_send(nc, io->buf, io->len);  // Echo message back
      mbuf_remove(io, io->len);       // Discard message from recv buffer
      nc->flags |= MG_F_SEND_AND_CLOSE;
      break;
    default:
      break;
  }
}

int main(void) {
  struct mg_mgr mgr;
  const char *port1 = "udp://1234", *port2 = "udp://127.0.0.1:17000";

  mg_mgr_init(&mgr, NULL);
  mg_bind(&mgr, port1, ev_handler);
  mg_bind(&mgr, port2, ev_handler);

  printf("Starting echo mgr on ports %s, %s\n", port1, port2);
  for (;;) {
    mg_mgr_poll(&mgr, 1000);
  }
  mg_mgr_free(&mgr);

  return 0;
}

And here are the problems which are reported trying to include the Link header:

cmake --build .                                          19:44:58
Scanning dependencies of target Carabiner
[ 33%] Building C object CMakeFiles/Carabiner.dir/mongoose.c.o
[ 66%] Building CXX object CMakeFiles/Carabiner.dir/carabiner.cpp.o
In file included from /Users/jim/git/carabiner/carabiner.cpp:21:
In file included from /Users/jim/git/link/include/ableton/Link.hpp:25:
In file included from /Users/jim/git/link/include/ableton/platforms/Config.hpp:22:
In file included from /Users/jim/git/link/include/ableton/link/Controller.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/Service.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/PeerGateways.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/InterfaceScanner.hpp:22:
In file included from /Users/jim/git/link/include/ableton/platforms/asio/AsioWrapper.hpp:54:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio.hpp:19:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/associated_executor.hpp:21:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/system_executor.hpp:19:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/scheduler.hpp:20:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/error_code.hpp:185:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/impl/error_code.ipp:29:
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/socket_types.hpp:300:9: error: 
      unknown type name 'ip_mreq'
typedef ip_mreq in4_mreq_type;
        ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/socket_types.hpp:304:9: error: 
      unknown type name 'ipv6_mreq'
typedef ipv6_mreq in6_mreq_type;
        ^
In file included from /Users/jim/git/carabiner/carabiner.cpp:21:
In file included from /Users/jim/git/link/include/ableton/Link.hpp:25:
In file included from /Users/jim/git/link/include/ableton/platforms/Config.hpp:22:
In file included from /Users/jim/git/link/include/ableton/link/Controller.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/Service.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/PeerGateways.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/InterfaceScanner.hpp:22:
In file included from /Users/jim/git/link/include/ableton/platforms/asio/AsioWrapper.hpp:54:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio.hpp:19:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/associated_executor.hpp:21:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/system_executor.hpp:19:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/scheduler.hpp:21:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/execution_context.hpp:406:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/impl/execution_context.hpp:20:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/service_registry.hpp:20:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/mutex.hpp:25:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/posix_mutex.hpp:71:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/impl/posix_mutex.ipp:24:
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/error.hpp:169:33: error: 
      use of undeclared identifier 'ESHUTDOWN'
  shut_down = ASIO_SOCKET_ERROR(ESHUTDOWN),
                                ^
In file included from /Users/jim/git/carabiner/carabiner.cpp:21:
In file included from /Users/jim/git/link/include/ableton/Link.hpp:25:
In file included from /Users/jim/git/link/include/ableton/platforms/Config.hpp:22:
In file included from /Users/jim/git/link/include/ableton/link/Controller.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/Service.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/PeerGateways.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/InterfaceScanner.hpp:22:
In file included from /Users/jim/git/link/include/ableton/platforms/asio/AsioWrapper.hpp:54:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio.hpp:21:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/basic_datagram_socket.hpp:21:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/datagram_socket_service.hpp:30:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/reactive_socket_service.hpp:30:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/reactive_socket_accept_op.hpp:24:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/socket_holder.hpp:20:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/socket_ops.hpp:333:
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/impl/socket_ops.ipp:120:21: error: 
      use of undeclared identifier 'SO_NOSIGPIPE'
        SOL_SOCKET, SO_NOSIGPIPE, &optval, sizeof(optval)), ec);
                    ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/impl/socket_ops.ipp:1405:21: error: 
      use of undeclared identifier 'SO_NOSIGPIPE'
        SOL_SOCKET, SO_NOSIGPIPE, &optval, sizeof(optval)), ec);
                    ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/impl/socket_ops.ipp:1498:23: error: 
      use of undeclared identifier 'SO_REUSEPORT'
          SOL_SOCKET, SO_REUSEPORT, optval, optlen);
                      ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/impl/socket_ops.ipp:2415:37: error: 
      no member named 'getipnodebyaddr' in the global namespace
  hostent* retval = error_wrapper(::getipnodebyaddr(
                                  ~~^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/impl/socket_ops.ipp:2470:37: error: 
      no member named 'getipnodebyname' in the global namespace
  hostent* retval = error_wrapper(::getipnodebyname(
                                  ~~^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/impl/socket_ops.ipp:2499:7: error: 
      no type named 'freehostent' in the global namespace
    ::freehostent(h);
    ~~^
In file included from /Users/jim/git/carabiner/carabiner.cpp:21:
In file included from /Users/jim/git/link/include/ableton/Link.hpp:25:
In file included from /Users/jim/git/link/include/ableton/platforms/Config.hpp:22:
In file included from /Users/jim/git/link/include/ableton/link/Controller.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/Service.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/PeerGateways.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/InterfaceScanner.hpp:22:
In file included from /Users/jim/git/link/include/ableton/platforms/asio/AsioWrapper.hpp:54:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio.hpp:78:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/ip/basic_resolver.hpp:28:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/ip/resolver_service.hpp:29:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolver_service.hpp:25:
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolve_endpoint_op.hpp:70:22: error: 
      use of undeclared identifier 'NI_MAXHOST'
      char host_name[NI_MAXHOST];
                     ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolve_endpoint_op.hpp:71:25: error: 
      use of undeclared identifier 'NI_MAXSERV'
      char service_name[NI_MAXSERV];
                        ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolve_endpoint_op.hpp:73:43: error: 
      use of undeclared identifier 'NI_MAXHOST'
          o->endpoint_.size(), host_name, NI_MAXHOST, service_name, NI_MAXSERV,
                                          ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolve_endpoint_op.hpp:73:69: error: 
      use of undeclared identifier 'NI_MAXSERV'
          o->endpoint_.size(), host_name, NI_MAXHOST, service_name, NI_MAXSERV,
                                                                    ^
In file included from /Users/jim/git/carabiner/carabiner.cpp:21:
In file included from /Users/jim/git/link/include/ableton/Link.hpp:25:
In file included from /Users/jim/git/link/include/ableton/platforms/Config.hpp:22:
In file included from /Users/jim/git/link/include/ableton/link/Controller.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/Service.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/PeerGateways.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/InterfaceScanner.hpp:22:
In file included from /Users/jim/git/link/include/ableton/platforms/asio/AsioWrapper.hpp:54:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio.hpp:78:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/ip/basic_resolver.hpp:28:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/ip/resolver_service.hpp:29:
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolver_service.hpp:93:20: error: 
      use of undeclared identifier 'NI_MAXHOST'
    char host_name[NI_MAXHOST];
                   ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolver_service.hpp:94:23: error: 
      use of undeclared identifier 'NI_MAXSERV'
    char service_name[NI_MAXSERV];
                      ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolver_service.hpp:96:20: error: 
      use of undeclared identifier 'NI_MAXHOST'
        host_name, NI_MAXHOST, service_name, NI_MAXSERV,
                   ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/resolver_service.hpp:96:46: error: 
      use of undeclared identifier 'NI_MAXSERV'
        host_name, NI_MAXHOST, service_name, NI_MAXSERV,
                                             ^
In file included from /Users/jim/git/carabiner/carabiner.cpp:21:
In file included from /Users/jim/git/link/include/ableton/Link.hpp:25:
In file included from /Users/jim/git/link/include/ableton/platforms/Config.hpp:22:
In file included from /Users/jim/git/link/include/ableton/link/Controller.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/Service.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/PeerGateways.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/InterfaceScanner.hpp:22:
In file included from /Users/jim/git/link/include/ableton/platforms/asio/AsioWrapper.hpp:54:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio.hpp:83:
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/ip/icmp.hpp:58:17: error: 
      use of undeclared identifier 'IPPROTO_ICMPV6'
    return icmp(ASIO_OS_DEF(IPPROTO_ICMPV6),
                ^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/socket_types.hpp:318:25: note: 
      expanded from macro 'ASIO_OS_DEF'
# define ASIO_OS_DEF(c) ASIO_OS_DEF_##c
                        ^
<scratch space>:61:1: note: expanded from here
ASIO_OS_DEF_IPPROTO_ICMPV6
^
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/detail/socket_types.hpp:331:37: note: 
      expanded from macro 'ASIO_OS_DEF_IPPROTO_ICMPV6'
# define ASIO_OS_DEF_IPPROTO_ICMPV6 IPPROTO_ICMPV6
                                    ^
In file included from /Users/jim/git/carabiner/carabiner.cpp:21:
In file included from /Users/jim/git/link/include/ableton/Link.hpp:25:
In file included from /Users/jim/git/link/include/ableton/platforms/Config.hpp:22:
In file included from /Users/jim/git/link/include/ableton/link/Controller.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/Service.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/PeerGateways.hpp:22:
In file included from /Users/jim/git/link/include/ableton/discovery/InterfaceScanner.hpp:22:
In file included from /Users/jim/git/link/include/ableton/platforms/asio/AsioWrapper.hpp:54:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio.hpp:84:
In file included from /Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/ip/multicast.hpp:20:
/Users/jim/git/link/cmake_include/../modules/asio-standalone/asio/include/asio/ip/detail/socket_option.hpp:403:25: error: 
      member reference base type 'asio::detail::in6_mreq_type' (aka 'int') is
      not a structure or union
      memcpy(ipv6_value_.ipv6mr_multiaddr.s6_addr, bytes.data(), 16);
             ~~~~~~~~~~~^~~~~~~~~~~~~~~~~
fatal error: too many errors emitted, stopping now [-ferror-limit=]
20 errors generated.
make[2]: *** [CMakeFiles/Carabiner.dir/carabiner.cpp.o] Error 1
make[1]: *** [CMakeFiles/Carabiner.dir/all] Error 2
make: *** [all] Error 2

Warning: multi-character character constant

Hi,
When building link code I get the following warnings:

../../../third-party/ableton-link/include/ableton/link/Timeline.hpp:43:11: warning: multi-character character constant [-Wmultichar]
     key = 'tmln'
           ^~~~~~
../../../third-party/ableton-link/include/ableton/link/PayloadEntries.hpp:35:11: warning: multi-character character constant [-Wmultichar]
     key = '__ht'
           ^~~~~~
../../../third-party/ableton-link/include/ableton/link/PayloadEntries.hpp:73:11: warning: multi-character character constant [-Wmultichar]
     key = '__gt'
           ^~~~~~
../../../third-party/ableton-link/include/ableton/link/PayloadEntries.hpp:111:11: warning: multi-character character constant [-Wmultichar]
     key = '_pgt'
           ^~~~~~
../../../third-party/ableton-link/include/ableton/link/MeasurementEndpointV4.hpp:34:11: warning: multi-character character constant [-Wmultichar]
     key = 'mep4'
           ^~~~~~
../../../third-party/ableton-link/include/ableton/link/SessionId.hpp:38:11: warning: multi-character character constant [-Wmultichar]
     key = 'sess'
           ^~~~~~

Multi-character constants is implementation defined... so I would suggest to convert them to explicit integer values and maybe leave a comment in the code.

http://scarff.id.au/blog/2009/c-multi-character-character-constants/

Get Beat syncing worked in Console

Hi everyone , i have a short question :)
How Can i make an Application with Link integreated that prints Out a Line to Console every time my Main Computer so the DJ Controller makes a Beat so from the BPM Line... Can someone help me with it i am Not best c++ Developer :D

Remove 20BPM minimum limitation

Is there a reason for the minimum BPM to be 20? I currently have users that require BPM lower than this and my app previously supposed it. Is there a technical reason to limit the BPM?

Getting quantum without AudioPlatform on a non-audio application

Hi there,

I'm working on an application (Linux, Windows, MacOS) that synchronizes to Link and doesn't need to produce any sound. Actually it drives a microcontroller to display information.

Thanks to the LinkHut sample project, I managed to get almost all the information I need (tempo in bpm, beat count).

But I can't figure out how to get the quantum a simple way (I mean beat signature, like 4/4, 5/4 and so on).

Oh well, Of course I could mimic LinkHut and integrate the AudioEngine/AudioPlatform in my app, but isn't there a lightweight method to obtain this value from the Timeline object for example? I'd like to be as audio-driver-independant as possible.

Many thanks for your help,

Nico

Can't connect to my own app on windows

Hi,
i have some problem with the link connection between app,
it's a little bit complicated :
my app can connect to any other app who got link, and the numPeers update succefully on windows and mac
on mac, i can connect 2 or more instances of my app and the numPeers update succesfully and it work with other app to
but on windows if i try to connect a second instance of my app on the same or on a other computer they don't detect each other, i have to connect an other app or a mac instance of my app to they can connect to it and be synchronize and the numPeers of the session is incorrect. All the windows instances of my app count like 1 in the session.
I don't know what to do :(
Sorry for my bad English

Cordially
Pablo

[question] Web midi support

Hi,

Have you ever thought about making this accessible into the web ? It would be nice if we could use that combined with webassembly and web midi api.

Thanks for replies :)

Regards.

Start-Stop-Sync

Hi, is there anything that needs to be done to enable this for OSX?

I've built from the branch and am running LinkHut - start stop sync always shows as off even if I run up Live and enable it. In my own code I don't seem to be getting any callbacks when the play state changes. thx

QLinkHut segfaults when clicking on 'Play' (jack)

I'm building current HEAD (d4fb22b), on Debian/sid (amd64) (with g++-6, ignoring the issue #16 for now), including the QT examples, and have manually enabled JACK support:

$ mkdir build
$ cd build
$ cmake -DLINK_BUILD_QT_EXAMPLES=ON -DLINK_BUILD_JACK=ON ..
$ make -j -k
[...]
$

This gives me LinkHut, QLinkHut and QLinkHutSilent in bin/)

  • running bin/LinkHut seems to work
    • i get audible clicks
    • keystrokes work
    • running multiple instances, they sync
  • running bin/QLinkHutSilent seems to work as well
    • i get no audible clicks (expected)
    • clicking on Link i get 0 Links or 1 Links depending on the existance of other (Q)LinkHutSilence instances
    • instances sync
    • clicking on Play i see a colourful beat visualisation
  • running bin/QLinkHut almost works
    • i get no audible clicks
    • clicking on Link i get 0 Links or 1 Links depending on the existance of other (Q)LinkHutSilence instances
    • instances sync
    • clicking on Play i get a segfault ๐Ÿ˜ข
$ gdb ./bin/QLinkHut
(gdb) run
Starting program: /foo/bar/ableton-link/build/bin/QLinkHut 
[Thread debugging using libthread_db enabled]
Using host libthread_db library "/lib/x86_64-linux-gnu/libthread_db.so.1".
[New Thread 0x7fffee96d700 (LWP 12022)]
[New Thread 0x7fffee16c700 (LWP 12023)]
[New Thread 0x7fffed96b700 (LWP 12024)]
[New Thread 0x7fffed8ea700 (LWP 12025)]
[New Thread 0x7fffed869700 (LWP 12026)]
[New Thread 0x7fffe1810700 (LWP 12028)]
[New Thread 0x7fffd840f700 (LWP 12029)]
[New Thread 0x7fffd7c0e700 (LWP 12030)]
[New Thread 0x7fffd740d700 (LWP 12031)]
[New Thread 0x7fffd6c0c700 (LWP 12032)]
[New Thread 0x7fffd61d3700 (LWP 12033)]
[New Thread 0x7fffd48f7700 (LWP 12034)]

Thread 6 "QLinkHut" received signal SIGSEGV, Segmentation fault.
[Switching to Thread 0x7fffed869700 (LWP 12026)]
0x00007ffff77bcfe0 in ?? () from /usr/lib/x86_64-linux-gnu/libjack.so.0
(gdb) bt
#0  0x00007ffff77bcfe0 in ?? () from /usr/lib/x86_64-linux-gnu/libjack.so.0
#1  0x00007ffff77bd7c1 in ?? () from /usr/lib/x86_64-linux-gnu/libjack.so.0
#2  0x0000555555730d25 in ableton::linkaudio::AudioPlatform::audioCallback(unsigned int) ()
#3  0x0000555555730c2e in ableton::linkaudio::AudioPlatform::audioCallback(unsigned int, void*) ()
#4  0x00007ffff77ba01e in ?? () from /usr/lib/x86_64-linux-gnu/libjack.so.0
#5  0x00007ffff77b97e8 in ?? () from /usr/lib/x86_64-linux-gnu/libjack.so.0
#6  0x00007ffff77d1040 in ?? () from /usr/lib/x86_64-linux-gnu/libjack.so.0
#7  0x00007ffff7591464 in start_thread (arg=0x7fffed869700) at pthread_create.c:333
#8  0x00007ffff5bdf9df in clone () at ../sysdeps/unix/sysv/linux/x86_64/clone.S:105

Additional build paths for MSVC projects

The additional paths needs to be provided which aren't documented:

link\build\modules\ASIOSDK2.3\common
link\modules\asio-standalone\asio\include
link\examples\linkaudio
link\build\modules\ASIOSDK2.3\host
link\build\modules\ASIOSDK2.3\host\pc

renderMetronomeIntoBuffer from audio file

Sorry for possible nubie question, but I have some trouble with understanding starter example - console metronome. To best understand the example I tried to change simple cosinus signal at renderMetronomeIntoBuffer to some wav file from asset - so we will have to play wav file on each beat.

Could you provide some advice how I need to fill mBuffer with data from wav (or any other audio file). I read wav and produce huge float array for 300 ms file. How could I place it inside mBuffer correctly? Or any other example different from cos / sin functions, but generated audio data?

Any suggestions will be appreciated, thanks in advance.

Could not get Audio Device

Hi, I'm trying to run LinkHut example on an Ubuntu PC.
Portaudio is installed and everything compiles fine, but when I try to run the LinkHut example I get the Error:

Could not get Audio Device.
terminate called without an active exception
Aborted (core dumpled)

Thats strange, cause on my Raspberry Pi 3 there are no problems to run this 0.o
Does someone has an idea what can I do to solve this?

'asio': ambiguous symbol

Hi,

I'm having this ambiguity issue when compiling on Windows with MSVC2017.

Both Link and Asio are in my include path. Curiously this ambiguity problem doesn't happen on Mac OSX.

The only work around I have found so far was renaming Link's asio namespace to asiowrapper and updating all the references to it.

Any other way of doing this?

Thanks!

asio\include\asio/basic_io_object.hpp(222): error C2872: 'asio': ambiguous symbol
asio\include\asio/impl/write_at.hpp(35): note: could be 'asio'
link\include\ableton/platforms/asio/Util.hpp(28): note: or 'ableton::platforms::asio'
asio\include\asio/basic_io_object.hpp(222): note: while compiling class template member function 'asio::basic_io_objectasio::detail::win_iocp_handle_service,true::basic_io_object(asio::io_context &)'
asio\include\asio/windows/overlapped_handle.hpp(81): note: see reference to function template instantiation 'asio::basic_io_objectasio::detail::win_iocp_handle_service,true::basic_io_object(asio::io_context &)' being compiled
asio\include\asio/windows/overlapped_handle.hpp(58): note: see reference to class template instantiation 'asio::basic_io_objectasio::detail::win_iocp_handle_service,true' being compiled
asio\include\asio/use_future.hpp(137): note: see reference to class template instantiation 'asio::use_future_t<std::allocator>::std_allocator_void' being compiled
asio\include\asio/use_future.hpp(145): note: see reference to class template instantiation 'asio::use_future_t<std::allocator>' being compiled

Android Link implementation: ableton::Link::enable

I am working on an implementation of Ableton Link on the Android platform. The Link singleton lives in a C++ code base interfacing the Java app with JNI, and interacts with an audio callback defined with OpenSL ES. Link and the Timeline functions return desirable parameters - beat time, phase, etc. so it would seem as though the system configuration, discovery configuration, and the JNI linking is successful. The app is stable and running smoother with the new Link implementation than it has before (your linear regression implementation is great!).

However, I am unable to enable Link. The Link::enable() method is not thread safe, this much is clear, but with the function restricted to a header, I am having a lot of trouble debugging the crash that follows the Link::enable() function call. Within the JNI code (which presumably is all contained within the audio thread), I explicitly create a new thread to make the call - tried with both the C++ std::thread functions and the p_thread_create() functions to no avail.

Would it be possible to provide an example within the context of link/examples/linkaudio/AudioEngine.cpp, demonstrating a function call to Link::enable?

Link crashing on Android with Qt?

I'm having a crash every time I set Link enable(true) on Android. The same doesn't happens on Windows, Mac and iOS. I use Qt to develop all my apps. This is what I get on the console output by the time of the crash:

F libc    : stack corruption detected
F libc    : Fatal signal 6 (SIGABRT), code -6 in tid 13715 (qtMainLoopThrea)

Have you ever had any similar behaviour?

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.