title: Uncaught Kotlin exception: kotlin.native.IncorrectDereferenceException: illegal attempt to access non-shared
body: <p>I try to use the Kotlin MPP(Multiplatform) to develop a shared library between Android and iOS. But I face the problem about threading in iOS. For my application in iOS, I establish the object in main thread but it probably calls the function in the other thread and throw this exception as following:</p>
  
  <pre><code>Uncaught Kotlin exception: kotlin.native.IncorrectDereferenceException: illegal attempt to access non-shared example.api.DrivingBehaviorDetector@397cba8 from other thread
          at 0   DrivingBehaviorDetector             0x00000001037619d7 kfun:kotlin.Throwable.&lt;init&gt;(kotlin.String?)kotlin.Throwable + 87
          at 1   DrivingBehaviorDetector             0x000000010375bca5 kfun:kotlin.Exception.&lt;init&gt;(kotlin.String?)kotlin.Exception + 85
          at 2   DrivingBehaviorDetector             0x000000010375b9a5 kfun:kotlin.RuntimeException.&lt;init&gt;(kotlin.String?)kotlin.RuntimeException + 85
          at 3   DrivingBehaviorDetector             0x0000000103781395 kfun:kotlin.native.IncorrectDereferenceException.&lt;init&gt;(kotlin.String)kotlin.native.IncorrectDereferenceException + 85
          at 4   DrivingBehaviorDetector             0x0000000103782568 ThrowIllegalObjectSharingException + 744
          at 5   DrivingBehaviorDetector             0x00000001037d72bc _ZNK27BackRefFromAssociatedObject19ensureRefAccessibleEv + 76
          at 6   DrivingBehaviorDetector             0x00000001037c97c3 -[KotlinBase toKotlin:] + 35
          at 7   DrivingBehaviorDetector             0x00000001037e3ef1 Kotlin_ObjCExport_refFromObjC + 65
          at 8   DrivingBehaviorDetector             0x00000001037c4e37 objc2kotlin.125 + 167
          at 9   Test                                0x000000010340224d $sIeg_IeyB_TR + 45 (/Users/james/Documents/Projects/go/TestMPPforiOS/&lt;compiler-generated&gt;:&lt;unknown&gt;)
          at 10  libdispatch.dylib                   0x0000000103959dd4 _dispatch_call_block_and_release + 12
          at 11  libdispatch.dylib                   0x000000010395ad48 _dispatch_client_callout + 8
          at 12  libdispatch.dylib                   0x000000010396c460 _dispatch_root_queue_drain + 819
          at 13  libdispatch.dylib                   0x000000010396cb96 _dispatch_worker_thread2 + 132
          at 14  libsystem_pthread.dylib             0x00007fff5245f6b3 _pthread_wqthread + 583
          at 15  libsystem_pthread.dylib             0x00007fff5245f3fd start_wqthread + 13
  (lldb) 
  </code></pre>
  
  <p>I survey the solution in these articles:</p>
  
  <p>Immutability in Kotlin/Native: <a href="https://kotlinlang.org/docs/reference/native/immutability.html" rel="nofollow noreferrer">Immutability in Kotlin/Native</a></p>
  
  <p>Coroutines and Immutability of K/N: <a href="https://medium.com/quick-code/kotlin-native-ios-a1a73d7390fe" rel="nofollow noreferrer">Coroutines and Immutability of K/N</a>.</p>
  
  <p>The entrance of my API(shared library) as following:</p>
  
  <pre><code>class DrivingBehaviorDetector (
      private var gravity:Vector?,
      private var front:Vector?,
      onGravityOrFrontChanged: ((newGravity: Vector?, newFront: Vector?, timestamp: Long) -&gt; Unit)?,
      onDrivingEventDetected: ((event: DrivingEvent) -&gt; Unit)?
  ) {
  
      private val lowPassFilter = LowPassFilter()
      private val accProcessor = AccProcessor(gravity, front, onGravityOrFrontChanged, onDrivingEventDetected)
  
      init {
          gravity = gravity?.toCoreUnit()
          front = front?.toCoreUnit()
      }
  
      fun addData(data:Acceleration) {
          val rawAcc = data.toCoreUnit()
          val filterAcc = lowPassFilter.lowPass(rawAcc)
          accProcessor.addData(filterAcc)
      }
  
      fun addData(data:List&lt;Acceleration&gt;) {
          for(acc in data) {
              addData(acc)
          }
      }
  }
  </code></pre>
  
  <p>We can notice the API is so simple as feeding a lot of data and callback the results from some calculations. But in the iOS throw the exception and code as following:</p>
  
  <pre class="lang-swift prettyprint-override"><code>let drivingBehaviorDetector = DrivingBehaviorDetector(gravity: nil, front: nil, onGravityOrFrontChanged: { (newGravity, newFront, timestamp) in
      print("newGravity = \(newGravity)")
      print("newFront = \(newFront)")
  }) { (event) in
      print("event = \(event.description())")
  }
  
  let acc1 = Acceleration(vector: Vector(x: 0, y: 0, z: 0))
  let acc2 = Acceleration(vector: Vector(x: 0, y: 100, z: 0))
  
  drivingBehaviorDetector.addData(data: acc1)
  
  DispatchQueue.global(qos: .background).async {
      drivingBehaviorDetector.addData(data: acc2)
  }
  </code></pre>
  
  <p>The only one solution I can imagine is forcing to use API in the same thread but this seems to a little strange. Is it possible to solve this issue by modifying the shared library. Because mu usage is simple as only one "DrivingBehaviorDetector" but it could be calling the "addData" function in the different thread. Thanks for answering. </p>